iOS 网络与存储编程原理|青训营笔记

169 阅读10分钟

这是我参与「第四届青训营」笔记创作活动的的第二十天。本篇文章将会简单介绍iOS网络与存储编程原理。

首先看一看对于iOS存储与网络的大体关系:

image.png

引用:juejin.cn/post/712345…

一、了解App存储与网络的作用

网络存储服务器是什么?作用是什么?

网络存储器就像一台只有存储功能的电脑终端,可以独立工作的,系统是固化的,但可以自己配置,有的需要先接入服务器或电脑进行设置,有的像路由器一样直接配置,后者居多而且更方便。对于服务器来说,现在流行的网络存储器基本上是以网上邻居形式出现,当然如果设置映射网络驱动器的话,可以当本地磁盘来用。它可以数据集中存储、数据共享、数据保护以及通过网络传输的形式进行数据互通保存备份。

系统IO

流程讲解: image.png

引用:www.cnblogs.com/cxuanBlog/p…

计算机组成指的是系统结构的逻辑实现,包括机器机内的数据流和控制流的组成及逻辑设计等。 主要分为五个部分:控制器,运算器,存储器,输入设备,输出设备。

什么是IO设备?

I/O 设备又叫做输入/输出设备,它是人类用来和计算机进行通信的外部硬件。它是在主存和外部设备(例如磁盘驱动器、终端和网络)之间复制数据的过程。输入操作是从 I/O 设备复制数据到主存,而输出操作是从主存复制数据到 I/O 设备。

网络编程

两个通信设备(具有网卡)通过网络进行数据的传播与交换

概论:

  • 建立连接:通过IP或者域名来连接两台设备,通过端口号找到对应的通信程序
  • 通信协议:要传输的数据需要根据约定的格式来创建,或者接受的数据需要按照约定的格式来还原
  • 数据传输方式:双工、长链接、可靠的,如TCP传输协议,单工、广播、不可靠的,如UDP传输协议
  • TCP/IP分层模式:将复杂的网络通信分拆,层的功能独立,下层为上层提供服务
  • TCP连接:三次握手

还有一些新概念要掌握。我们需要理解基本的客户端 - 服务器(C/S)编程模型,以及如何编写使用因特网提供的服务的客户端程序。最后,我们将把所有这些概念结合起来,开发一个虽小但功能齐全的待办事项Demo。

二、iOS文件管理与序列化

macOS中常用目录:

  • /Applications Self explanatory, this is where your Mac’s applications are kept
  • /Developer The Developer directory appears only if you have installed Apple’s Developer Tools, and no surprise, contains developer related tools, documentation, and files.
  • /Library Shared libraries, files necessary for the operating system to function properly, including settings, preferences, and other necessities (note: you also have a Libraries folder in your home directory, which holds files specific to that user).
  • /Network largely self explanatory, network related devices, servers, libraries, etc
  • /System System related files, libraries, preferences, critical for the proper function of Mac OS X
  • /Users All user accounts on the machine and their accompanying unique files, settings, etc. Much like /home in Linux
  • /Volumes Mounted devices and volumes, either virtual or real, such as hard disks, CD’s, DVD’s, DMG mounts, etc
  • / Root directory, present on virtually all UNIX based file systems. Parent directory of all other files
  • /bin Essential common binaries, holds files and programs needed to boot the operating system and run properly
  • /etc Machine local system configuration, holds administrative, configuration, and other system files
  • /dev Device files, all files that represent peripheral devices including keyboards, mice, trackpads, etc
  • /usr Second major hierarchy, includes subdirectories that contain information, configuration files, and other essentials used by the operating system
  • /sbin Essential system binaries, contains utilities for system administration
  • /tmp Temporary files, caches, etc
  • /var Variable data, contains files whose contents change as the operating system runs

/Applications

此目录是您安装供计算机的所有用户使用的应用程序的地方。App Store 将用户购买的应用程序自动安装到此目录中。该Utilities子目录包含用于管理本地系统的应用程序子集。此目录是本地域的一部分。

/Library

系统上有多个Library目录,每个目录与不同的域或特定用户相关联。应用程序应使用该Library目录来存储特定于应用程序(或特定于系统)的资源。有关此目录的内容以及如何使用它来支持您的应用程序的详细信息,请参阅库目录存储应用程序特定文件。

/Network

此目录包含局域网中的计算机列表。无法保证位于网络文件服务器上的文件将/Network在其路径的开头具有目录。路径名称取决于几个因素,包括网络卷的安装方式。例如,如果用户使用 Connect to Server 命令安装卷,则路径以/Volumes目录开头。编写代码时,假设除引导卷之外的任何卷上的文件都可以位于基于网络的服务器上。

/System

此目录包含 macOS 运行所需的系统资源。这些资源由 Apple 提供,不得修改。该目录包含系统域的内容。

/Users

该目录包含一个或多个用户主目录。用户主目录是存储用户相关文件的地方。典型用户的主目录包括以下子目录:

  • Applications- 包含用户特定的应用程序。
  • Desktop— 包含用户桌面上的项目。
  • Documents— 包含用户文档和文件。
  • Downloads— 包含从 Internet 下载的文件。
  • Library— 包含用户特定的应用程序文件(隐藏在 macOS 10.7 及更高版本中)。
  • Movies— 包含用户的视频文件。
  • Music— 包含用户的音乐文件。
  • Pictures— 包含用户的照片。
  • Public— 包含用户想要分享的内容。
  • Sites— 包含用户个人站点使用的网页。(必须启用 Web 共享才能显示这些页面。)
  • 上述目录仅用于存储用户文档和媒体。除非用户明确指示,否则应用不得将文件写入上述目录。此规则的唯一例外是Library目录,应用程序可能会使用该目录来存储支持当前用户所需的数据文件。

在子目录中,只有该Public目录可供系统上的其他用户访问。默认情况下限制对其他目录的访问。

/Volumes

挂载的设备和卷,无论是虚拟的还是真实的,例如硬盘、CD、DVD、DMG 挂载等

/

根目录,存在于几乎所有基于 UNIX 的文件系统上。所有其他文件的父目录

/bin

基本的通用二进制文件,包含引导操作系统和正常运行所需的文件和程序

/etc

机器本地系统配置,保存管理、配置和其他系统文件

/dev

设备文件,所有代表外围设备的文件,包括键盘、鼠标、触控板等

/usr

第二个主要层次结构,包括包含操作系统使用的信息、配置文件和其他必需品的子目录

/sbin

基本系统二进制文件,包含用于系统管理的实用程序

/tmp

临时文件、缓存等

/var

可变数据,包含内容随操作系统运行而变化的文件

三、iOS网络编程

C/S模式

C/S模式是计算机软件协同工作的一种模式,通常采取两层结构,指的是客户端/服务器模式。(C是指Client,S是指Server)

image.png

引用:juejin.cn/post/712345…

HTTP请求

在一次Http请求的行为中, 发起请求的是客户端、做出响应的是服务器。其实一些场景下客户端也可能作为服务器(比如消息推送,长链接指令,点对点通信),如同上图的解析。

1. NSURLConnectiong

//同步get请求
// 1.创建请求路径(url)
NSURL *url = [NSURL URLWithString:@""];

// 2.通过请求路径(url)创建请求对象(request)
NSURLRequest *request = [NSURLRequest requestWithURL:url];

// 3.向服务器发送同步请求(data)
NSData *data = [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
// sendSynchronousRequest阻塞式的方法,等待服务器返回数据

// 4.解析服务器返回的数据(解析成字符串)
NSString *string = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];

//异步get请求
// 1.创建请求路径(url)
NSURL *url = [NSURL URLWithString:@""];

// 2.通过请求路径(url)创建请求对象(request)
NSURLRequest *request = [NSURLRequest requestWithURL:url];

// 3.向服务器发送异步请求
[NSURLConnection sendAsynchronousRequest:request queue:[[NSOperationQueue alloc] init] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
    // 请求完毕会来到这个block

// 4.解析服务器返回的数据(解析成字符串)
    NSString *string = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
    NSLog(@"%@", string);
}];

//通过代理发现异步请求
// 1.创建请求路径(url)
NSURL *url = [NSURL URLWithString:@""];

// 2.通过请求路径(url)创建请求对象(request)
NSURLRequest *request = [NSURLRequest requestWithURL:url];

// 3.通过代理创建连接对象
[NSURLConnection connectionWithRequest:request delegate:self];

// [[NSURLConnection alloc] initWithRequest:request delegate:self];

// NSURLConnection *conn = [[NSURLConnection alloc] initWithRequest:request delegate:self startImmediately:NO];
// startImmediately:是否立即发送请求

// 开始发送请求
// [conn start];

// 取消发送请求
// [conn cancel];

//同步post请求
// 1.创建请求路径(url)
NSURL *url = [NSURL URLWithString:@""];

// 2.通过请求路径(url)创建请求对象(request)
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
// 更改请求方法
request.HTTPMethod = @"POST";
// 设置请求体
request.HTTPBody = [@"" dataUsingEncoding:NSUTF8StringEncoding];
// 设置超时(5秒后超时)
request.timeoutInterval = 5;
// 设置请求头(非必要,看情况)
//    [request setValue:@"iOS 9.0" forHTTPHeaderField:@"User-Agent"];

// 3.向服务器发送同步请求
[NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];

//异步post请求
// 1.创建请求路径(url)
NSURL *url = [NSURL URLWithString:@""];

// 2.通过请求路径(url)创建请求对象(request)
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
// 更改请求方法
request.HTTPMethod = @"POST";
// 设置请求体
request.HTTPBody = [@"" dataUsingEncoding:NSUTF8StringEncoding];
// 设置超时(5秒后超时)
request.timeoutInterval = 5;
// 设置请求头
// [request setValue:@"iOS 9.0" forHTTPHeaderField:@"User-Agent"];

// 3.向服务器发送异步请求
[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
    if (connectionError) { // 比如请求超时
        NSLog(@"----请求失败");
    } else {
        NSLog(@"------%@", [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]);
    }
}];

//NSURLConnection 中文URL处理
NSString *urlStr = @"";
// 将中文URL进行转码
urlStr = [urlStr stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
NSURL *url = [NSURL URLWithString:urlStr];

2. NSURLSession

// 第一种GET请求
// 获得NSURLSession对象
NSURLSession *session = [NSURLSession sharedSession];

// 创建任务
NSURLSessionDataTask *task = [session dataTaskWithRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:@""]] completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
    NSLog(@"%@", [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:nil]);
}];

// 启动任务
[task resume];

// 第二种GET请求
// 获得NSURLSession对象
NSURLSession *session = [NSURLSession sharedSession];

// 创建任务
NSURLSessionDataTask *task = [session dataTaskWithURL:[NSURL URLWithString:@""] completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
    NSLog(@"%@", [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:nil]);
}];

// 启动任务
[task resume];

//post请求
// 获得NSURLSession对象
NSURLSession *session = [NSURLSession sharedSession];

// 创建请求
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@""]];
request.HTTPMethod = @"POST"; // 请求方法
request.HTTPBody = [@"" dataUsingEncoding:NSUTF8StringEncoding]; // 请求体

// 创建任务
NSURLSessionDataTask *task = [session dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
    NSLog(@"%@", [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:nil]);
}];

// 启动任务
[task resume];

//通过代理发送请求
// 获得NSURLSession对象
NSURLSession *session = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration] delegate:self delegateQueue:[[NSOperationQueue alloc] init]];

// 创建任务
NSURLSessionDataTask *task = [session dataTaskWithRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:@""]]];

// 启动任务
[task resume];
#pragma mark - <NSURLSessionDataDelegate>

// 1.接收到服务器的响应
-(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveResponse:(NSURLResponse *)response completionHandler:(void (^)(NSURLSessionResponseDisposition))completionHandler
{
    // 允许处理服务器的响应,才会继续接收服务器返回的数据
    completionHandler(NSURLSessionResponseAllow);
    // void (^)(NSURLSessionResponseDisposition)
}

// 2.接收到服务器的数据(可能会被调用多次)
-(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveData:(NSData *)data
{
    NSLog(@"%s", __func__);
}

// 3.请求成功或者失败(如果失败,error有值)
-(void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error
{
    NSLog(@"%s", __func__);
}

引用:www.jianshu.com/p/8a90aa6ba…

Reference

《iOS 网络与存储编程原理》juejin.cn/post/712345…

《网络存储服务器是什么?网络存储服务器有什么作用?》www.huaweicloud.com/zhishi/edit…

《操作系统IO全流程讲解》www.cnblogs.com/cxuanBlog/p…

《iOS网络编程》www.jianshu.com/p/ecf853976…

《文件系统基础》developer.apple.com/library/arc…

《Mac OS X 目录结构解释》osxdaily.com/2007/03/30/…

《iOS 网络:HTTP 请求》www.jianshu.com/p/8a90aa6ba…