QAuth 2.0

news2024/11/18 22:51:57

OAuth 2.0授权框架支持第三方支持访问有限的HTTP服务,通过在资源所有者和HTTP服务之间进行一个批准交互来代表资源者去访问这些资源,或者通过允许第三方应用程序以自己的名义获取访问权限。

为了方便理解,可以想象OAuth2.0就是在用户资源和第三方应用之间的一个中间层,它把资源和第三方应用隔开,使得第三方应用无法直接访问资源,从而起到保护资源的作用。为了访问这种受保护的资源,第三方应用(客户端)在访问的时候需要提供凭证。即,需要告诉OAuth2.0你是谁你要做什么。你可以将用户名和密码告诉第三方应用,让第三方应用直接以你的名义去访问,也可以授权第三方应用去访问。可以联想一下微信公众平台开发,在微信公众平台开发过程中当我们访问某个页面,页面可能弹出一个提示框应用需要获取我们的个人信息问是否允许,点确认其实就是授权第三方应用获取我们在微信公众平台的个人信息。这里微信网页授权就是使用的OAuth2.0。

介绍

在传统的client-server认证模型中,客户端通过提供资源所有者的凭证来请求服务器访问一个受限制的资源(受保护的资源)。为了让第三方应用可以访问这些受限制的资源,资源所有者共享他的凭证给第三方应用。

Roles

QAuth定义了四种角色:

  • resource owner(资源所有者)

  • resource server(资源服务器)

  • client(客户端):代表资源所有者并且经过所有者授权去访问受保护的资源的应用程序

  • authorization server(授权服务器):在成功验证资源所有者并获得授权后向客户端发出访问令牌

Protocol Flow

抽象的OAuth2.0流程如图所示:

  1. (A) 客户端向资源所有者请求其授权

  2. (B) 客户端收到资源所有者的授权许可,这个授权许可是一个代表资源所有者授权的凭据

  3. (C) 客户端向授权服务器请求访问令牌,并出示授权许可

  4. (D) 授权服务器对客户端身份进行认证,并校验授权许可,如果都是有效的,则发放访问令牌

  5. (E) 客户端向资源服务器请求受保护的资源,并出示访问令牌

  6. (F) 资源服务器校验访问令牌,如果令牌有效,则提供服务

Authorization Client

一个授权许可是一个凭据,它代表资源所有者对访问受保护资源的一个授权,是客户端用来获取访问令牌的。

授权类型

授权类型有四种:

  • authorization code:用户登录授权,先拿code,用code换token

  • implicit:用户登录授权,不拿code了,直接拿token

  • resource owner password credentials:验证客户端,直接用用户名和密码,拿token

  • client credentials:验证客户端,直接拿token

Authorization Code(授权码)

授权码是授权服务器用来获取并作为客户端和资源所有者之间的中介。代替直接向资源所有者请求授权,客户端定向资源所有者到一个授权服务器,授权服务器反过来指导资源所有者将授权码返回给客户端。在将授权码返回给客户端之前,授权服务器对资源所有者进行身份验证并获得授权。因为资源所有者只对授权服务器进行身份验证,所以资源所有者的凭据永远不会与客户机共享。

Implicit

隐式授权是为了兼顾到在浏览器中用诸如JavaScript的脚本语言实现的客户端而优化的简化授权代码流程。在隐式授权流程中,不是发给客户端一个授权码,而是直接发给客户端一个访问令牌,而且不会对客户端进行认证。隐式授权提高了一些客户端(比如基于浏览器实现的客户端)的响应能力和效率,因为它减少了获得访问令牌所需的往返次数。

Resource Owner Password Credentials(客户端的验证授权)

资源所有者的密码凭据(比如,用户名和密码)可以直接作为授权许可来获取访问令牌。这个凭据只应该用在高度信任的资源所有者和客户端之间(比如,客户端是系统的一部分,或者特许的应用),并且其它授权模式不可用的时候。

Client Credentials(客户端凭据)

客户端凭据通常用作授权许可

Access Token

访问令牌是用来访问受保护的资源的凭据。一个访问令牌是一个字符串,它代表发给客户端的授权。令牌代表资源所有者授予的对特定范围和访问的时间(PS:令牌是有范围和有效期的),并由资源服务器和授权服务器强制执行。访问令牌可以有不同的格式、结构和使用方法。

Refresh Token

Refresh Token是用于获取Access Token的凭据。刷新令牌是授权服务器发给客户端的,用于在当前访问令牌已经失效或者过期的时候获取新的访问令牌。刷新令牌只用于授权服务器,并且从来不会发给资源所有者。

刷新的流程如图所示:

  1. (A) 客户端请求获取访问令牌,并向授权服务器提供授权许可

  2. (B) 授权服务器对客户端身份进行认证,并校验授权许可,如果校验通过,则发放访问令牌和刷新令牌

  3. (C) 客户端访问受保护的资源,并向资源服务器提供访问令牌

  4. (D) 资源服务器校验访问令牌,如果校验通过,则提供服务

  5. (E) 重复(C)和(D)直到访问令牌过期。如果客户端直到访问令牌已经过期,则跳至(G),否则不能继续访问受保护的资源

  6. (F) 自从访问令牌失效以后,资源服务器返回一个无效的令牌错误

  7. (G) 客户端请求获取一个新的访问令牌,并提供刷新令牌

  8. (H) 授权服务器对客户端进行身份认证并校验刷新令牌,如果校验通过,则发放新的访问令牌(并且,可选的发放新的刷新令牌)

Client Registration(客户端注册)

在使用该协议之前,客户端向授权服务器注册。

Client Types

QAuth定义了两种客户端类型:

  • confidential: 能够维护其凭证的机密性的客户端

  • public:不能维护其凭证的机密性的客户端

Client Password

拥有客户端密码的客户端可以使用HTTP Basic向服务器进行认证,当然前提是授权服务器支持HTTP Basic认证。

例如:Authorization: Basic czZCaGRSa3F0Mzo3RmpmcDBaQnIxS3REUmJuZlZkbUl3

二者选其一的,授权服务器可能支持在请求体中用下列参数包含客户端凭据:

  • client_id:必须的,在授权服务器中注册过的客户端标识符。

  • client_secret:必须的,客户端秘钥。如果秘钥是空字符串的话可以省略该参数。

用这两个参数将客户端凭据包含在请求体中这种方式不推荐,并且应该限制客户端不能直接用HTTP Basic认证方案。

Protocal Endpoints(协议端点)

授权处理用两个授权服务器端点:

  • Authorization endpoint:用于客户端从资源所有者那里获取授权

  • Token endpoint:用于客户端用授权许可交互访问令牌

还有一个端点

  • Redirection endpoint:用于资源服务器通过资源所有者用户代理将包含授权凭据的响应返回给客户端

Authorization Endpoint

授权端点用于和资源所有者交互并获取一个授权许可的。授权服务器必须首先校验资源所有者的身份。

Response Type

客户端用以下参数通知授权服务器自己渴望的授权类型:

  • response_type:必须的,为了请求一个授权码这个值必须是"code",为了请求一个访问令牌这个值必须是"token"

Redirection Endpoint

在完成和资源所有者的交互以后,授权服务器直接将资源所有者的user-agent返回给客户端。授权服务器重定向到这个user-agent

Access Token Scope

授权和令牌端点允许客户端使用“scope”请求参数指定访问请求的范围。反过来,授权服务器使用“scope”响应参数通知客户机它所发放的访问令牌的范围。

Obtaining Authorization

为了获得一个访问令牌,客户端需要先从资源所有者那里获得授权。授权是以授权许可的形式来表示的。

OAuth定义了四种授权类型:

  • authorization code

  • Implicit

  • resource owner password credentials

  • client credentials

Authorization Code Grant

授权码流程如图所示:

  1. (A) 客户端通过将资源所有者的用户代理指向授权端点来启动这个流程。客户端包含它的客户端标识符,请求范围,本地状态,和重定向URI,在访问被允许(或者拒绝)后授权服务器立即将用户代理返回给重定向URI。

  2. (B) 授权服务器验证资源所有者(通过用户代理),并确定资源所有者是否授予或拒绝客户端的访问请求。

  3. (C) 假设资源所有者授权访问,那么授权服务器用之前提供的重定向URI(在请求中或在客户端时提供的)将用户代理重定向回客户端。重定向URI包括授权码和前面客户端提供的任意本地状态。

  4. (D) 客户端用上一步接收到的授权码从授权服务器的令牌端点那里请求获取一个访问令牌。

  5. (E) 授权服务器对客户端进行认证,校验授权码,并确保这个重定向URI和第三步(C)中那个URI匹配。如果校验通过,则发放访问令牌,以及可选的刷新令牌。

Implicit Grant

隐式授权用于获取访问令牌(它不支持刷新令牌),它针对已知的操作特定重定向URI的公共客户端进行了优化。这些客户端通常在浏览器中使用脚本语言(如JavaScript)实现。因为它是基于重定向的流程,所以客户端必须有能力和资源所有者的用户代理(典型地,是一个Web浏览器)进行交互,同时必须有能力接收来自授权服务器的重定向请求。隐士授权类型不包含客户端身份验证,它依赖于资源所有者的存在和重定向URI的注册。由于访问令牌被编码到重定向URI中,所以它可能暴露给资源所有者以及同一台设备上的其它应用。

隐式授权流程如图所示:

  1. (A) 客户端引导资源所有者的user-agent到授权端点。客户端携带它的客户端标识,请求scope,本地state和一个重定向URI。

  2. (B) 授权服务器对资源所有者(通过user-agent)进行身份认证,并建立连接是否资源所有者允许或拒绝客户端的访问请求。

  3. (C) 假设资源所有者允许访问,那么授权服务器通过重定向URI将user-agent返回客户端。

  4. (D) user-agent遵从重定向指令

  5. (E) web-hosted客户端资源返回一个web页面(典型的,内嵌脚本的HTML文档),并从片段中提取访问令牌。

  6. (F) user-agent执行web-hosted客户端提供的脚本,提取访问令牌

  7. (G) user-agent将访问令牌传给客户端

Resource Owner Password Credentials Grant

资源所有者密码凭证授予类型适用于资源所有者与客户端(如设备操作系统或高度特权应用程序)存在信任关系的情况。授权服务器在启用这种授予类型时应该特别小心,并且只在其他授权流程不可行的时候才允许使用。这种授权类型适合于有能力维护资源所有者凭证(用户名和密码,典型地,用一个交互式的表单)的客户端。

资源所有者密码凭证流程如图:

  1. (A) 资源所有者提供他的用户名和密码给客户端

  2. (B) 客户端携带从资源所有者那里收到的凭证去授权服务器的令牌端点那里请求获取访问令牌

  3. (C) 授权服务器对客户端进行身份认证,并校验资源所有者的凭证,如果都校验通过,则发放访问令牌

Client Credentials Grant

客户端用它自己的客户单凭证去请求获取访问令牌

客户端凭证授权流程如图所示:

  1. (A) 客户端用授权服务器的认证,并请求获取访问令牌

  2. (B) 授权服务器验证客户端身份,如果严重通过,则发放令牌

Spring Security OAuth 2.0

OAuth 2.0 Provider 实现

在OAuth 2.0中,provider角色事实上是把授权服务和资源服务分开,有时候它们也可能在同一个应用中,用Spring Security OAuth你可以选择把它们分成两个应用,当然多个资源服务可以共享同一个授权服务。

获取token的请求由Spring MVC的控制端点处理,访问受保护的资源由标准的Spring Security请求过滤器处理。

为了实现OAuth 2.0授权服务器,在Spring Security的过滤器链中需要有以下端点:

  • AuthorizationEndpoint 用于服务授权请求。默认URL是/oauth/authorize

  • TokenEndpoint 用于服务访问令牌请求。默认URL是/oauth/token

在OAuth 2.0的资源服务器中需要实现下列过滤器:

  • OAuth2AuthenticationProcessingFilter 用于加载认证

对于所有的OAuth 2.0 provider特性,最简单的配置是用Spring OAuth @Configuration适配器。

Authorization Server 配置

只要你配置了授权服务器,那么你应该考虑客户端用于获取access token的授权类型(例如,授权码,用户凭证,刷新token)。服务器的配置是用来提供client detail服务和token服务的,并且可以启用或者禁用全局的某些机制。

每个客户端可以配置不同的权限

@EnableAuthorizationServer注解被用来配置授权服务器,也可以和实现了AuthorizationServerConfigurer接口的任意被标记为@Bean的Bean一起来对授权服务器进行配置。

下列特性被委托给AuthorizationServerConfigurer:

  • ClientDetailsServiceConfigurer :a configurer that defines the client details service

  • AuthorizationServerSecurityConfigurer :defines the security constraints on the token endpoint

  • AuthorizationServerEndpointsConfigurer :defines the authorization and token endpoints and the token services

一件重要的事情是,provider配置了将授权码给OAuth客户端的方式(PS:在授权码类型授权过程中)

OAuth客户端通过将end-user(最终用户)导向授权页,用户可用在此输入他的凭证。之后,授权服务器携带授权码通过重定向的方式将授权码返回给客户端。

配置 Client Details

ClientDetailsServiceConfigurer可用使用client details service的两种实现中的任意一种:in-memory 或者 JDBC

客户端重要的属性是:

  • clientId :(必须的)客户端ID

  • secret :(对于信任的客户端需要)客户端秘钥

  • scope :客户端被限定的范围。如果scope为定义或者为空(默认为空)则客户端不受scope限制

  • authorizedGrantTypes :客户端使用到的授权类型

  • authorities :授予客户端的权限

客户端details可以在应用运行时被更新,通过直接访问存储(例如:如果用JdbcClientDetailsService的话可以实时改变数据库表中的数据)或者通过实现ClientDetailsManager接口(它们也都实现了ClientDetailsService接口)。

注意:用于JDBC服务的数据库schema并没有打包到library中(因为你再实际使用的时候可能有诸多差异)

管理Tokens

AuthorizationServerTokenServices定义了管理OAuth 2.0 Token所必须的操作。请注意:

  • 当创建一个access token的时候,这个认证必须被存储起来,以便后续访问资源的时候对接收到的access token进行引用校验。

  • access token用来加载认证

当你实现了AuthorizationServerTokenServices接口,你可能考虑用DefaultTokenServices。有许多内置的插件化的策略可以用来改变access token的格式和存储。

默认情况下,用随机值来生成token,并且用TokenService来处理所有(除了token持久化以外)事情。默认的存储是in-memory实现,但是有其它的实现可以使用。

  • 对于单服务器而言,默认的InMemoryTokenStore是完美的。大多数的项目是从这里开始的,为了使它很容易启动,也不需要其它依赖,并且可能以开发模式进行操作。

  • JdbcTokenStore是JDBC版本的Token存储。它把Token数据存储到关系型数据库中。为了使用JdbcTokenStore需要classpath下有"spring-jdbc"。

  • JSON Web Token (JWT) 它将授权的token的所有数据进行编码后存储(没有使用后端存储是它最大的优势)。这种方式的一个缺点是你不能很容易的撤销一个access token,因此一般用该方式存储的token的有效期很短,并且在刷新token的时候之前的token会被废除。另一个缺点是,token很长,因为它里面存了很多关于用户凭证的信息。JwtTokenStore不会真的存储数据,它不持久化任何数据。但是在DefaultTokenServices中,它扮演着token值和认证信息转换的角色。

注意:对于JDBC的schema没有打包到library中,确保用@EnableTransactionManagement来防止多个客户端在同一行创建token。注意,示例中的schema都有明确地主键声明,在并发环境中这是必须的。

JWT Tokens

为了使用JWT Tokens,你需要在你的授权服务器中有一个JwtTokenStore。资源服务器也需要解码这个token,所以JwtTokenStore有一个依赖JwtAccessTokenConverter,相同的实现需要被包含在授权服务器和资源服务器中。也就是说,授权服务器和资源服务器中都需要JwtTokenStore实现。默认情况下,token是被签名的,而且资源服务器必须能够校验这个签名,因此需要有相同的对称key,或者需要公钥来匹配授权服务器上的私钥。公钥被授权服务器暴露在/oauth/token_key端点,默认情况下这个端点的访问规则是"denyAll()"。你可以用标准的SpEL表达式(例如:permitAll())到AuthorizationServerSecurityConfigurer来开放它。

为了使用JwtTokenStore,在classpath下需要有"spring-security-jwt"

Grant Types

授权类型通过AuthorizationEndpoint来支持。默认情况下,除了password以外,所有授权类型都支持。下面是授权类型的一些属性:

  • authenticationManager :通过注入一个AuthenticationManager来切换成password授权

  • userDetailsService :如果你注入一个UserDetailsService或者以任意方式配置了一个全局的UserDetailsService(例如:在GlobalAuthenticationManagerConfigurer中),那么一个刷新token将被包含在user detail中,为了强制账户是激活的。

  • authorizationCodeServices :定义授权码服务(AuthorizationCodeServices的实例)

  • implicitGrantService :在隐式授权期间管理状态

  • tokenGranter :tokenGranter

Configuring the Endpoint URLs

AuthorizationServerEndpointsConfigurer有一个pathMapping()方法。它有两个参数:

  • 端点的默认URL路径

  • 自定义的路径(必须以"/"开头)

下面是框架提供的URL路径:

  • /oauth/authorize 授权端点

  • /oauth/token 令牌端点

  • /oauth/confirm_access 用户批准授权的端点

  • /oauth/error 用于渲染授权服务器的错误

  • /oauth/check_token 资源服务器解码access token

  • /oauth/check_token 当使用JWT的时候,暴露公钥的端点

授权端点/oauth/authorize应该被保护起来,以至于它只能被认证过的用户访问。

注意:如果您的授权服务器同时也是一个资源服务器的话,那么就有另一个具有较低优先级的安全过滤器链来控制API资源。通过访问令牌来保护这些请求,你需要它们的路径不能与主用户过滤器链中的那些相匹配,所以请确保包含一个请求matcher,它只挑选出上面的WebSecurityConfigurer中的非api资源。

Customizing the UI

授权服务器的大多数端点主要都是被机器使用的,但是有两个资源是需要UI,它们分别是/oauth/confirm_access和HTML响应/oauth/error。框架为它们提供的实现是空白页,真实的情况是大多数授权服务器可能想要提供它们自己的实现来控制样式和内容。所以,你需要做的事情就是提供一个Spring MVC 被标注了@RequestMappings注解的Controller来映射这些端点,并且框架将用一个低的优先级来发放请求。在默认的/oauth/confirm_access你期望一个AuthorizationRequest绑定到session。你可以抓取请求的所有数据并按照自己喜欢的方式渲染它们,然后用户需要做的就是向/oauth/authorize发送关于批准或拒绝授予的信息。默认的UserApprovalHandler取决于是否你再AuthorizationServerEndpointsConfigurer中提供了一个ApprovalStore。标准的审批处理器如下:

  • TokenStoreUserApprovalHandler :通过user_oauth_approval做一个简单的yes/no决定等同于“true”或“false”

  • ApprovalStoreUserApprovalHandler :一组"scope*"参数key。参数的值可以是"true"或者"approval"。至少有一个scope是approval才算是授权成功。(A grant is successful if at least one scope is approved.)

强制SSL

纯HTTP对于测试来说是可以的,但是在生成中授权服务器应该使用SSL。你可以在一个安全的容器或代理后面运行应用程序,如果你正确地设置代理和容器(这与OAuth2无关),那么它应该可以正常工作。对于/authorize端点你需要把它当作正常的应用安全的一部分来做,对于/token端点在AuthorizationServerEndpointsConfigurer中有一个标记可以设置,通过用sslOnly()方法。

自定义错误处理

授权服务器用标准的Spring MVC特性来进行错误处理。

你可以提供自己的实现,通过添加@Controller并且带上@RequestMapping("/oauth/error")

Mapping User Roles to Scopes

有时候,为了限制token的scope,不仅仅要根据指定的客户端的范围,也要根据用户自己的权限来进行限制。如果你在你的AuthorizationEndpoint用DefaultOAuth2RequestFactory,你可以设置checkUserScopes=true来限制匹配的用户角色的允许范围。AuthorizationServerEndpointsConfigurer允许你注入一个自定义的OAuth2RequestFactory

资源服务器配置

一个资源服务器(可能与授权服务器是相同的应用,也可能与授权服务器是分开的应用)通过OAuth2 Token服务受保护的资源。Spring OAuth 提供一个Spring Security认证过滤器来实现这个保护。你可以在一个@Configuration类上用@EnableResourceServer来切换它,并且用ResourceServerConfigurer配置它。下列特性可以被配置:

  • tokenServices :一个ResourceServerTokenServices的实例

  • resourceId :资源ID(推荐的,如果存在的话会被授权服务器校验)

  • 资源服务器的其它扩展端点

  • request matchers for protected resources (defaults to all)

  • access rules for protected resources (defaults to plain "authenticated")

  • 其它通过HttpSecurity配置的自定义的受保护的资源

@EnableResourceServer注释将自动添加一个OAuth2AuthenticationProcessingFilter类型的过滤器到Spring安全过滤器链中。

OAuth 2.0 客户端

受保护的资源配置

受保护的资源(或者叫远程资源)可以用OAuth2ProtectedResourceDetails类型的bean来定义。一个被保护的资源由下列属性:

  • id :资源的id。这个id只是用于客户端查找资源。

  • clientId :OAuth Client id。

  • clientSecret :关联的资源的secret。默认非空

  • accessTokenUri :提供access_token的端点的uri

  • scope :逗号分隔的字符串,代表访问资源的范围。默认为空

  • clientAuthenticationScheme :客户端认证所采用的schema。建议的值:"http_basic"和"form"。默认是"http_basic"。

不同的授权类型有不同的OAuth2ProtectedResourceDetails的具体实现(例如:ClientCredentialsResourceDetails是"client_credentials"类型的具体实现)

  • userAuthorizationUri :用户授权uri,非必需的。

客户端配置

对于OAuth 2.0客户端配置,简化的配置用@EnableOAuth2Client。这个注解做两件事情:

  • 创建一个过滤器(ID是oauth2ClientContextFilter)来存储当前的请求和上下文。在请求期间需要进行身份认证时,它管理重定向URI。

  • 在请求范围内创建一个AccessTokenRequest类型的bean。对于授权代码(或隐式)授予客户端是很有用的,可以避免与单个用户相关的状态发生冲突。

访问受保护的资源

建议用RestTemplate访问受保护的资源。Spring Security为OAuth提供了一个扩展的RestTemplate只需要你提供一个OAuth2ProtectedResourceDetails的实例即可。为了使它和用户token(授权码方式授权)一起使用,你应该考虑用@EnableOAuth2Client配置。

一般来说,web应用程序不应该使用密码授予,因此如果您可以支持AuthorizationCodeResourceDetails,请避免使用ResourceOwnerPasswordResourceDetails。为了和用户令牌(授权码)一起使用,你应该考虑用@EnableOAuth2Client配置。

客户端持久化Token

客户端不需要持久化令牌,但是最好不要在每次重启客户端应用程序时都要求用户批准新的令牌授予。

ClientTokenServices接口定义了为特定用户保存OAuth 2.0令牌所需的操作。这是一个JDBC实现,但是如果您希望实现自己的服务,以便在持久数据库中存储访问令牌和相关的身份验证实例,则可以这样做。如果你想要使用这个特性,你需要为OAuth2RestTemplate提供一个经过特殊配置的TokenProvider。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1573339.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

多路转接-epoll/Reactor(2)

epoll 上次说到了poll,它存在效率问题,因此出现了改进的poll----epoll。 目前epoll是公认的效率最高的多路转接的方案。 快速了解epoll接口 epoll_create: 这个参数其实已经被废弃了。 这个值只要大于0就可以了。 这是用来创建一个epoll模…

用友U9 存在PatchFile.asmx接口任意文件上传漏洞

声明: 本文仅用于技术交流,请勿用于非法用途 由于传播、利用此文所提供的信息而造成的任何直接或者间接的后果及损失,均由使用者本人负责,文章作者不为此承担任何责任。 简介 用友U9是由中国用友软件股份有限公司开发的一款企业…

FJSP:狐猴优化算法(Lemurs Optimizer,LO)求解柔性作业车间调度问题(FJSP),提供MATLAB代码

一、柔性作业车间调度问题 柔性作业车间调度问题(Flexible Job Shop Scheduling Problem,FJSP),是一种经典的组合优化问题。在FJSP问题中,有多个作业需要在多个机器上进行加工,每个作业由一系列工序组成&a…

Linux(Ubuntu)中创建【samba】服务,用于和Windows系统之间共享文件

目录 1.先介绍一下什么是Samba 2.安装,配置服务 安装 配置(smb.conf) 配置用户 3.出现的问题(Failed to add entry for user XXXX) 4.创建文件夹 5.windows访问 1.先介绍一下什么是Samba Samba是一个开源的软…

HTML5.Canvas简介

1. Canvas.getContext getContext(“2d”)是Canvas元素的方法,用于获取一个用于绘制2D图形的绘图上下文对象。在给定的代码中,首先通过getElementById方法获取id为"myCanvas"的Canvas元素,然后使用getContext(“2d”)方法获取该Ca…

剑指Offer题目笔记26(动态规划的基础知识)

面试题88: 问题: ​ 一个数组cost的所有数字都是正数,它的第i个数字表示在一个楼梯的第i级台阶往上爬的成本,在支付了成本cost[i]之后可以从第i级台阶往上爬1级或2级。请计算爬上该楼梯的最少成本。 解决方案一:&…

【简单讲解下epoll】

🎥博主:程序员不想YY啊 💫CSDN优质创作者,CSDN实力新星,CSDN博客专家 🤗点赞🎈收藏⭐再看💫养成习惯 ✨希望本文对您有所裨益,如有不足之处,欢迎在评论区提出…

Day:004(1) | Python爬虫:高效数据抓取的编程技术(数据解析)

数据解析-正则表达式 在前面我们已经搞定了怎样获取页面的内容,不过还差一步,这么多杂乱的代码夹杂文字我们怎样 把它提取出来整理呢?下面就开始介绍一个十分强大的工具,正则表达式! 正则表达式是对字符串操作的一种…

力扣Lc28---- 557. 反转字符串中的单词 III(java版)-2024年4月06日

1.题目描述 2.知识点 1)用StringBuilder的方法 实现可变字符串结果 最后返回的时候用.toString的方法 2)在Java中使用StringBuilder的toString()方法时,它会返回StringBuilder对象当前包含的所有字符序列的字符串表示。 在我们的例子中,sb是一个Stri…

Django之五种中间件定义类型—process_request、process_view、process_response.......

目录 1. 前言 2. 基础中间件 3. 如何自定义中间件 4. 五种自定义中间件类型 4.1 process_request 4.2 process_view 4.3 process_response 4.4 process_exception 4.5 process_template_response 5. 最后 1. 前言 哈喽,大家好,我是小K,今天咋们…

90天玩转Python-02-基础知识篇:初识Python与PyCharm

90天玩转Python系列文章目录 90天玩转Python—01—基础知识篇:C站最全Python标准库总结 90天玩转Python--02--基础知识篇:初识Python与PyCharm 90天玩转Python—03—基础知识篇:Python和PyCharm(语言特点、学习方法、工具安装) 90天玩转Python—04—基础知识篇:Pytho…

ubuntu20.04.6将虚拟机用户目录映射为磁盘Z

文章目录 linux虚拟机设置为NAT模式安装sshd服务映射目录到windows磁盘安装samba套件修改配置文件smb.conf重启smbd并设置用户名和密码 windows映射遇到的问题1、设置好之后映射不成功2、smbd下载失败3、smbd密码配置问题4、当有改动时候,最好重启一下smbd服务 linu…

图解大型网站多级缓存的分层架构

前言 缓存技术存在于应用场景的方方面面。从浏览器请求,到反向代理服务器,从进程内缓存到分布式缓存,其中缓存策略算法也是层出不穷。 假设一个网站,需要提高性能,缓存可以放在浏览器,可以放在反向代理服…

4月6号排序算法(2)

堆排序 讲堆排序之前我们需要了解几个定义 什么叫做最大堆,父亲节点,以及孩子节点 将根节点最大的堆叫做最大堆或大根堆,根节点最小的堆叫做最小堆或小根堆。 每个节点都是它的子树的根节点的父亲 。 反过来每个节点都是它父亲的孩子 。 …

post请求搜索功能爬虫

<!--爬虫仅支持1.8版本的jdk--> <!-- 爬虫需要的依赖--> <dependency> <groupId>org.apache.httpcomponents</groupId> <artifactId>httpclient</artifactId> <version>4.5.2</version> </dependency>…

「 典型安全漏洞系列 」11.身份验证漏洞详解

身份验证是验证用户或客户端身份的过程。网站可能会暴露给任何连接到互联网的人。这使得健壮的身份验证机制成为有效的网络安全不可或缺的一部分。 1. 什么是身份验证 身份验证即认证&#xff0c;是验证给定用户或客户端身份的过程。身份验证漏洞使攻击者能够访问敏感数据和功…

网络安全之命令注入

漏洞原理&#xff1a; 应用系统设计需要给用户提供指定的远程命令操作的接口&#xff0c;比如&#xff1a;路由器&#xff0c;防火墙&#xff0c;入侵检测等设备的web管理界面。一般会给用户提供一个ping操作的web界面 用户从web界面输入目标IP&#xff0c;提交后台会对改IP地…

C语言 练习题

目录 1.统计二进制中1的个数 方法1 方法2 方法3 2.求两个数二进制中不同位的个数 方法1 方法2 3.打印整数二进制的奇数位和偶数位 4.用“ * ”组成的X形图案 5.根据年份和月份判断天数 6.结语 1.统计二进制中1的个数 【题目内容】 写一个函数返回参数二进制中 1 的个…

MATLAB实现数值求解高阶常微分方程组

一、高阶常微分方程组 高阶常微分方程是指包含多个高阶常微分方程的系统。这些方程通常涉及多个未知函数及其高阶导数。解决高阶常微分方程组通常比解决单个高阶常微分方程更为复杂&#xff0c;因为需要同时考虑多个方程和多个未知函数之间的关系。 一般来说&#xff0c;解决…

数据库 06-03 时间戳

01.什么是时间戳 “时间戳是指格林威治时间1970年01月01日00时00分00秒(北京时间1970年01月01日08时00分00秒)起至现在的总秒数。通俗的讲, 时间戳是一份能够表示一份数据在一个特定时间点已经存在的完整的可验证的数据。 02.用时间戳实现调度 定义 数据库给予一个事务一个时…