<commit_before>//
//  Pipe.HTTP.swift
//  Monolith
//
//  Created by <NAME>. on 11/5/14.
//
//

import Foundation
import EonilPipe

extension Pipe {
	
	///	Task for `NSURLSessionDataTask`.
	///	Send and recieve small amount of data at once.
	public struct HTTPAtomicTranssmissionTask : Task {
		let	cachePolicy:NSURLRequestCachePolicy
		let	timeoutInterval:NSTimeInterval
		public func dispatch(signal: Incoming, _ observer: Outgoing -> ()) -> Cancel {
			let	ErrorDomain	=	"HTTPAtomicTransmissionTask"
			
			switch signal {
			case .Run(parameters: let ps1):
				let	u1	=	NSURL(scheme: ps1.security ? "https" : "http", host: ps1.host, path: ps1.path)!
				let	r1	=	NSMutableURLRequest(URL: u1, cachePolicy: cachePolicy, timeoutInterval: timeoutInterval)
				r1.HTTPMethod	=	ps1.method
				let	t1	=	NSURLSession.sharedSession().dataTaskWithRequest(r1) { (data:NSData!, response:NSURLResponse!, error:NSError!) -> Void in
					if let e1 = error {
						observer(HTTPAtomicTranssmissionTask.Outgoing.Unavailable(e1))
						return
					}
					if response == nil {
						observer(HTTPAtomicTranssmissionTask.Outgoing.Unavailable(NSError(domain: ErrorDomain, code: 0, userInfo: [NSLocalizedDescriptionKey: "There's no error, but also no response. HTTP(S) transmission failed."])))
						return
					}
					if data == nil {
						observer(HTTPAtomicTranssmissionTask.Outgoing.Unavailable(NSError(domain: ErrorDomain, code: 0, userInfo: [NSLocalizedDescriptionKey: "There's no error, but a response. Anyway data is provided as `nil`, so it is regarded as failure by an unknown error. HTTP(S) transmission failed."])))
						return
					}
					
					let	r2	=	response! as NSHTTPURLResponse
					let	hs1	=	collectHeaders(r2)
					let	r3	=	Outgoing.Response(status: r2.statusCode, headers: hs1, body: data)
					observer(HTTPAtomicTranssmissionTask.Outgoing.Available(r3))
				}
				
				t1.resume()
				return	{
					t1.cancel()
					observer(HTTPAtomicTranssmissionTask.Outgoing.Cancel)
				}
			}
		}
		
		public enum Incoming {
			case Run(parameters:Request)
			
			public struct Request {
				var	security:Bool
				var	method:String
				var	host:String
				var	port:Int
				var	path:String					///<	Will be encoded using RFC 3986. So do not passed encoded one.
				var	headers:[Header]
				var	body:NSData
			}
		}
		
		public enum Outgoing {
			
			///	Transmission just started and don't know yet the result.
			case Unknown
			
			///	Operation cancelled by calling the cance function.
			case Cancel
			
			///	Transmission successful. There's a response from the server.
			///	Take care that even `404` error from the server is regarded
			///	as success because it's also a response.
			case Available(Response)
			
			///
			case Unavailable(NSError)
			
			public struct Response {
				var	status:Int
				var	headers:[Header]
				var	body:NSData
			}
		}
		
		public typealias	Header	=	(name:String, value:String)
	}
	
	
	
	
	
	
	
	
	///	Task for `NSURLSessionDownloadTask`.
	///	Redirection will be handled automatically.
	public struct HTTPProgressiveDownloadTask : Task {
		public typealias	AuthenticationResolver	=	NSURLAuthenticationChallenge->(NSURLSessionAuthChallengeDisposition,NSURLCredential)
		
		///	Set an ID to be used for a parameter of `NSURLSessionConfiguration.backgroundSessionConfigurationWithIdentifier()` method call.
		public let	backgroundOperationID:String
		///	Will be used for any situation which requires authentication.
		public let	authenticationResolver:AuthenticationResolver?
		public func dispatch(signal: RequestSignal, _ observer: ResponseSignal -> ()) -> Cancel {
			
			
			struct GlobalQueue {
				static let	theQueue	=	NSOperationQueue()
			}
			
			final class Controller: NSObject, NSURLSessionDownloadDelegate {
				let	ErrorDomain	=	"HTTPProgressiveDownloadTask"
				let	observer:ResponseSignal->()
				let	authenticationResolver:AuthenticationResolver?
				private var	lastKnownCompletedOffset:Int64?
				init(observer:ResponseSignal->(), authenticationResolver:AuthenticationResolver?) {
					self.observer				=	observer
					self.authenticationResolver	=	authenticationResolver
				}
				private func URLSession(session: NSURLSession, downloadTask: NSURLSessionDownloadTask, didResumeAtOffset fileOffset: Int64, expectedTotalBytes: Int64) {
					let	r1	=	Range<Int64>(start: fileOffset, end: fileOffset)
					let	r2	=	expectedTotalBytes == NSURLSessionTransferSizeUnknown ? nil : Range<Int64>(start: 0, end: expectedTotalBytes) as Range<Int64>?<commit_msg>Added public initialiser to pipe task classes.<commit_after>//
//  Pipe.HTTP.swift
//  Monolith
//
//  Created by <NAME>. on 11/5/14.
//
//

import Foundation
import EonilPipe

extension Pipe {
	
	///	Task for `NSURLSessionDataTask`.
	///	Send and recieve small amount of data at once.
	public struct HTTPAtomicTranssmissionTask : Task {
		let	cachePolicy:NSURLRequestCachePolicy
		let	timeoutInterval:NSTimeInterval
		
		public init(cachePolicy:NSURLRequestCachePolicy, timeoutInterval:NSTimeInterval) {
			self.cachePolicy		=	cachePolicy
			self.timeoutInterval	=	timeoutInterval
		}
		
		public func dispatch(signal: Incoming, _ observer: Outgoing -> ()) -> Cancel {
			let	ErrorDomain	=	"HTTPAtomicTransmissionTask"
			
			switch signal {
			case .Run(parameters: let ps1):
				let	u1	=	NSURL(scheme: ps1.security ? "https" : "http", host: ps1.host, path: ps1.path)!
				let	r1	=	NSMutableURLRequest(URL: u1, cachePolicy: cachePolicy, timeoutInterval: timeoutInterval)
				r1.HTTPMethod	=	ps1.method
				let	t1	=	NSURLSession.sharedSession().dataTaskWithRequest(r1) { (data:NSData!, response:NSURLResponse!, error:NSError!) -> Void in
					if let e1 = error {
						observer(HTTPAtomicTranssmissionTask.Outgoing.Unavailable(e1))
						return
					}
					if response == nil {
						observer(HTTPAtomicTranssmissionTask.Outgoing.Unavailable(NSError(domain: ErrorDomain, code: 0, userInfo: [NSLocalizedDescriptionKey: "There's no error, but also no response. HTTP(S) transmission failed."])))
						return
					}
					if data == nil {
						observer(HTTPAtomicTranssmissionTask.Outgoing.Unavailable(NSError(domain: ErrorDomain, code: 0, userInfo: [NSLocalizedDescriptionKey: "There's no error, but a response. Anyway data is provided as `nil`, so it is regarded as failure by an unknown error. HTTP(S) transmission failed."])))
						return
					}
					
					let	r2	=	response! as NSHTTPURLResponse
					let	hs1	=	collectHeaders(r2)
					let	r3	=	Outgoing.Response(status: r2.statusCode, headers: hs1, body: data)
					observer(HTTPAtomicTranssmissionTask.Outgoing.Available(r3))
				}
				
				t1.resume()
				return	{
					t1.cancel()
					observer(HTTPAtomicTranssmissionTask.Outgoing.Cancel)
				}
			}
		}
		
		public enum Incoming {
			case Run(parameters:Request)
			
			public struct Request {
				var	security:Bool
				var	method:String
				var	host:String
				var	port:Int
				var	path:String					///<	Will be encoded using RFC 3986. So do not passed encoded one.
				var	headers:[Header]
				var	body:NSData
			}
		}
		
		public enum Outgoing {
			
			///	Transmission just started and don't know yet the result.
			case Unknown
			
			///	Operation cancelled by calling the cance function.
			case Cancel
			
			///	Transmission successful. There's a response from the server.
			///	Take care that even `404` error from the server is regarded
			///	as success because it's also a response.
			case Available(Response)
			
			///
			case Unavailable(NSError)
			
			public struct Response {
				var	status:Int
				var	headers:[Header]
				var	body:NSData
			}
		}
		
		public typealias	Header	=	(name:String, value:String)
	}
	
	
	
	
	
	
	
	
	///	Task for `NSURLSessionDownloadTask`.
	///	Redirection will be handled automatically.
	public struct HTTPProgressiveDownloadTask : Task {
		public typealias	AuthenticationResolver	=	NSURLAuthenticationChallenge->(NSURLSessionAuthChallengeDisposition,NSURLCredential)
		
		///	Set an ID to be used for a parameter of `NSURLSessionConfiguration.backgroundSessionConfigurationWithIdentifier()` method call.
		public let	backgroundOperationID:String
		///	Will be used for any situation which requires authentication.
		public let	authenticationResolver:AuthenticationResolver?
		
		public init(backgroundOperationID:String, authenticationResolver:AuthenticationResolver?) {
			self.backgroundOperationID	=	backgroundOperationID
			self.authenticationResolver	=	authenticationResolver
		}
		
		public func dispatch(signal: RequestSignal, _ observer: ResponseSignal -> ()) -> Cancel {
			
			
			struct GlobalQueue {
				static let	theQueue	=	NSOperationQueue()
			}
			
			final class Controller: NSObject, NSURLSessionDownloadDelegate {
				let	ErrorDomain	=	"HTTPProgressiveDownloadTask"
				let	observer:ResponseSignal->()
				let	authenticationResolver:AuthenticationResolver?
				private var	lastKnownCompletedOffset:Int64?
				init(observer:ResponseSignal->(), authenticationResolver:AuthenticationResolver?) {
					self.observer				=	observer
					self.authenticationResolver	=	authenticationResolver
				}
				private func URLSession(session: NSURLSession, downloadTask: NSURLSessionDownloadTask, didResumeAtOffset fileOffset: Int64, expectedTotalBytes: Int64) {
					let	r1	=	Range<Int64>(start: fileOffset, end: fileOffset)
					let	r2	=	expectedTotalBytes == NSURLSessionTransferSizeUnknown ? nil : Range<Int64>(start: 0, end: expectedTotalBytes) as Range<Int64>?
{'fraction_non_alphanumeric': 0.08727888994809872, 'fraction_numerical': 0.010803940260565617, 'mean_word_length': 3.662716049382716, 'pattern_counts': {'":': 0, '<': 13, '<?xml version=': 0, '>': 27, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 12, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2871771', 'n_tokens_mistral': 3476, 'n_tokens_neox': 2787, 'n_words': 753}