• Photo Realistic 高清照片风格

    1
    raw photo, photorealistic, masterpiece, best quality, hires, intricate details, reflections, photographed on a Canon EOS R5, 50mm lens, F/2.8, HDR, 8k resolution, ray-tracing,
  • Negative Prompt for Beauty

    1
    EasyNegative, bad_prompt_version2, bad-hands-5, ng_deepnegative_v1_75t, (watermark:1.6), (text:1.4), (worst quality:2), (low quality:2), (normal quality:2), lowres, normal quality, ((monochrome)), ((grayscale)), skin spots, acnes, skin blemishes, age spot, (outdoor:1.6), manboobs, backlight,(ugly:1.331), (duplicate:1.331), (morbid:1.21), (mutilated:1.21), (tranny:1.331), mutated hands, (poorly drawn hands:1.331), blurry, (bad anatomy:1.21), (bad proportions:1.331), extra limbs, (disfigured:1.331), (more than 2 nipples:1.331), (missing arms:1.331), (extra legs:1.331), (fused fingers:1.61051), (too many fingers:1.61051), (unclear eyes:1.331), bad hands, missing fingers, extra digit, (futa:1.1), bad body, pubic hair, glans, (nipples:1.4), (nsfw:1.4), (nude:1.6),nsfw,
  • Style 风格
    | Style | Description | Style | Description |

|——————-|————-|—————–|————-|
| artbook | 原画 | game_cg | 游戏CG |
| tachi-e | 立绘样式 | comic | 漫画 |
| dakimakura | 抱枕 | cosplay | 角色扮演 |
| photo | 照片 | personification | 拟人 |
| realistic | 现实 | sketch | 素描 |
| traditional_media | 手绘 | sketch | 手绘 |

  • Lighting Style
    | Lighting | Description | Lighting | Description |

|————————|————-|———————|————-|
| Bloom | 开花;绽放 | God rays | 神光;天光 |
| Hard shadows | 硬阴影 | Studio lighting | 工作室照明 |
| Soft lighting | 柔和照明;柔光 | Diffused lighting | 散射照明;漫射光 |
| Rim lighting | 边缘照明;边缘光 | Volumetric lighting | 体积照明 |
| Specular lighting | 镜面照明;高光 | Cinematic lighting | 电影照明 |
| Luminescence | 发光;自发光 | Translucency | 半透明性 |
| Subsurface scattering | 亚表面散射 | Global illumination | 全局照明 |
| Indirect light | 间接光 | Radiant light rays | 辐射光线 |
| Bioluminescent details | 生物发光细节 | Ektachrome | 依可透 |
| Glowing | 发光的 | Shimmering light | 闪闪发光的光 |
| Halo | 暈;光圈 | Iridescent | 彩虹色的;虹彩般的 |
| Backlighting | 背光;逆光 | Caustics | 光照色彩变化效应 |

  • Hair 头发
    | Hair | Description | Hair | Description |

|——————–|————-|——————–|————-|
| multicolored hair | 多彩的头发 | hime cut | 姬发式 |
| ahoge | 呆毛 | braid | 辫子 |
| asymmetrical hair | 半边刘海 | french braid | 法式辫 |
| blunt bangs | 齐刘海 | braided ponytail | 编织马尾辫 |
| parted bangs | 分开的刘海 | hair intakes | 进气口发型 |
| side swept bangs | 朝一个方向的刘海 | hair behind ear | 耳后发 |
| curtained hair | 窗帘式发型 | hair over shoulder | 披肩发 |
| colored inner hair | 内侧颜色 | hair bun | 团子头 |
| streaked hair | 条染 | double bun | 双团子头 |

  • Face 脸
    | Face | Description | Face | Description |

|————–|————-|—————–|————-|
| light smile | 微笑 | seductive smile | 诱惑笑 |
| grin | 露齿而笑 | laughing | 笑 |
| excited | 兴奋 | smirk | 微笑 |
| smug | 得意 屑 | embarrassed | 害羞 |
| shy | 害羞 | blush | 脸红 |
| sad | 悲伤的 | pout | 别扭 努嘴 |
| sigh | 叹气 | angry | 生气 |
| annoyed | 苦恼的 | frown | 皱眉/蹙额 |
| wide eyed | 睁大眼睛 | jitome | 鄙夷的眼神 |
| serious | 严肃 | smirk | 认真 |
| scowl | 锐利 | crazy | 疯狂的 |
| dark_persona | 黑化的 | naughty_face | 下流的表情 |
| endured_face | 忍耐的表情 | ahegao | 阿黑颜 |

  • Cloth 衣着
    | Cloth | Description | Cloth | Description |

|————————-|————–|———————-|————-|
| side-tie bikini bottom | 系带比基尼裤 | detached collar | 分离式衣领,只有衣领 |
| front-tie bikini top | 系带比基尼上衣 | cuffs | 袖口 |
| frilled bikini | 褶边比基尼 | midriff | 露腰上衣 |
| string bikini | 细带比基尼 | crop top | 露腰上衣 |
| highleg bikini | 高腰比基尼 | clothing cutout | 剪切过的衣服 |
| o-ring bikini | 有环的比基尼 | breast curtains | 胸帘 |
| sling bikini | 吊带比基尼 | versus bikini | 宝石比基尼 |
| mismatched bikini | 不太懂 | collared shirt | 带领衬衫 |
| revealing clothes | 暴露的衣服 | vest | 马甲背心 |
| see-through | 半透明衣服 | puffy sleeves | 蓬松袖子 |
| garter straps | 吊带袜 | peaked cap | 宽檐帽 |
| cheerleader | 啦啦队 | pelvic curtain | 骨盆帘 |
| pleated skirt | 百褶裙 | halter shirt | 吊带衬衫 |
| suspender skirt | 吊带裙 | ribbed sweater | 罗纹毛衣 |
| leotard | 连体紧身衣 | bodysuit | 连体紧身衣 |
| tank top | 汗衫 | torn clothes | 撕破的衣服 |
| taut clothes | 绷紧的衣服 | impossible clothes | 不可能的衣服 |
| string panties | 细绳内裤 | pantyhose | 连裤袜 |
| panties under pantyhose | 连裤袜下内裤 | competition swimsuit | 竞泳 |
| undersized clothes | 过小的衣服 | cropped jacket | 短外套 |
| plugsuit | 插入服,eva那种紧身衣 | crotchless panties | 开裆内裤 |
| legwear | 腿上一切 | serafuku | 水手服 |
| sailor collar | 水手领 | kimono | 和服 |
| yukata | 浴衣 | japanese clothes | 日式服装 |
| sports bra | 运动上衣 | bike shorts | 骑行裤 |
| lolita fashion | Lolita衣服 | race queen | 赛车女郎 |
| skindentation | 贴身的? | raglan sleeves | 连肩衣袖 |
| sleeves past fingers | 手指过长的袖子 | sleeves past wrist | 手腕过长的袖子 |
| bunnysuit | 兔女郎 | reverse bunnysuit | 逆兔女郎 |
| reverse outfit | 逆着穿的衣服 | straitjacket | 拘束衣 |
| sleeve skirts | 袖裙 | covered nipples | 凸激 |

  • Accessory 装饰
    Accessory Description Accessory Description
    tassel 流苏 wristband 腕带

| epaulettes | 肩章 | spaghetti strap | 细肩带 |
| ascot | 宽领带 | bridal gauntlets | 长手套 |
| trim | 包边 | criss-cross halter | 交错绕颈系带 |
| bowtie | 蝴蝶结领带 | halterneck | 绕颈系带 |
| neck ribbon | 系带领 | harness | 背带,挽具 |
| lapels | 翻领 | corset | 束腰 |
| frills | 荷叶边 | underbust | 束腰 |
| buckle | 扣带 | necklace | 项链 |
| belt buckle | 皮带扣 | sailor collar | 水手领 |
| chest harness | 胸带 | hairband | 发带 |
| suspenders | 肩吊带 | vambraces | 护腕 |
| lace-trimmed | 蕾丝边 | elbow gloves | 肘部手套 |
| veil | 面纱 | interface headset | 明日香头上那个角 |
| tinted eyewear | 有色眼镜 | chest jewel | 胸前珠宝 |
| pocket watch | 怀表 | tiara | 头冠 |
| hachimaki | 钵卷,日式头带 | fake animal ears | 假动物耳朵 |
| headgear | 头上机器 | hat bow | 帽子蝴蝶结 |
| sweatdrop | 汗珠 | pompom(clothes) | 衣服上的毛球 |
| water drop | 水滴 | pompom(cheerleading) | 啦啦队彩球 |
| falling petals | 掉落的花瓣 | neck ring | 颈环 |
| wrist cuffs | 手腕袖口 | stitches | 缝线 |
| chain | 锁链 | visor cap | 游客帽 |
| o-ring | 圆环装饰 | scrunchie | 发圈束 |
| oni horns | 鬼角 | surgical mask | 医用口罩 |
| mouth mask | 口罩 | | |

Pose 姿势

  • Full body 全身
    | Body Pose | Description | Body Pose | Description |

|——————–|————–|———————|————-|
| leaning forward | 前倾 | undressing | 脱衣服 |
| fetal position | 婴儿姿势(侧躺手脚曲着) | against wall | 靠墙 |
| on_stomach | 趴着 | squatting | 蹲下 |
| lying | 躺着 | sitting | 坐 |
| seiza | 正坐 | wariza/w-sitting | 割坐 |
| yokozuwari | 侧身坐 | indian_style | 盘腿 |
| leg_hug | 抱腿 | walking | 走 |
| running | 跑 | straddle | 跨坐 |
| straddling | 跨立 | kneeling | 下跪 |
| smoking | 抽烟 | arm_support | 用手支撑住 |
| caramelldansen | niconiconi | princess_carry | 公主抱 |
| fighting_stance | 战斗姿态 | upside-down | 颠倒的 |
| top-down_bottom-up | 趴着翘臀 | bent_over | 翘臀姿势 |
| all_fours | 四肢趴地 | arched_back | 弓身体 |
| back-to-back | 背对背 | symmetricalhandpose | 手对手 |
| eye_contact | 眼对眼(对视) | symmetrical_docking | 2女胸部贴在一起 |
| hug | 拥抱 | lap_pillow | 膝枕 |
| sleeping | 睡觉 | bathing | 洗澡 |
| mimikaki | 掏耳勺 | holding_hands | 牵手 |

  • Head 头

    Head Pose Description Head Pose Description
    head tilt 歪头 turning around 回头
    looking back 回头看 looking down 向下看
    looking up 向上看 smelling
  • Hand/Arm 手/手臂
    | Hand Pose | Description | Hand Pose | Description |

|——————-|————-|———————–|————-|
| handtomouth | 手放在嘴边 | arms_crossed | 手交叉于胸前 |
| arm at side | 手放头旁边 | hand on hip | 手放臀 |
| arms behind head | 手放脑后 | hand on another’s hip | |
| arms behind back | 手放后面 | handonhip | 单手插腰 |
| hand on own chest | 手放在自己的胸前 | handsonhips | 双手叉腰 |
| arms up/hands up | 举手 | stretch | 伸懒腰 |
| armpits | 举手露腋 | leg hold | 手把腿抓着 |
| grabbing | 抓住 | holding | 拿着 |
| fingersmile | 用手指做出笑脸 | skirt lift | 掀起裙子 |
| shirt lift | 掀起上衣 | adjusting_thighhigh | 调整过膝袜 |
| hair_pull | 拉头发 | hair scrunchie | 撮头发 |

  • Gestures 手势
    Gestures Description Gestures Description
    v/peace_symbol thumbs_up 翘大拇指
    middle_finger 比出中指 cat_pose 猫爪手势
    finger_gun 手枪手势 shushing 嘘手势
    waving 招手 salute 敬礼

| spread_arms | 张手 | | |

  • Leg 腿
    Leg Pose Description Leg Pose Description
    spread legs 张开腿 crossed legs 二郎腿
    fetal position 曲腿至胸 leg lift 抬一只脚
    legs up 抬两只脚

Environment 环境

  • General 总体

    Environment Description Environment Description
    cityscape 城市风景 landscape 风景
    indoors 室内 outdoors 室外
  • Color/Tone 色调

    Color/Tone Description Color/Tone Description
    light shade 阴凉处
    dark deep
    pale grey background 背景颜色(灰)
  • Weather 天气
    | Environment | Description | Environment | Description |

|———————-|————-|—————————|————-|
| golden hour lighting | 黄金时段照明 | in the rain | 雨中 |
| strong rim light | 强边缘光 | rainy days | 雨天 |
| night | 晚上 | sunset | 日落 |
| intense shadows | 强阴影 | cloudy | 多云 |
| full moon | 满月 | against backlight at dusk | 傍晚背对阳光 |

  • Indoor 室内

    Environment Description Environment Description
    mirror 反射 curtains 窗帘
    on bed 床上 on floor (wooden floor) 地板上
    on carpet 在地毯上 on yoga mats 在瑜伽垫上
    chair 椅子 magic circle 魔法阵
    poker table 赌桌
  • Outdoor 室外
    | Environment | Description | Environment | Description |

|————————————————–|————-|———————————————–|————-|
| mountain | 山 | ocean | 大海 |
| on a hill | 山上 | over the sea | 海边上 |
| the top of the hill | 山顶 | beautiful purple sunset at beach in the ocean | 海边日落 |
| beautiful detailed sky, beautiful detailed water | 好天好水 | sunset | 落日 |
| on the beach | 海滩上 | on the ocean | 在大海上 |
| meadow | 草地 | plateau | 高原 |
| desert | 沙漠 | | |

  • Plant 植被

    Environment Description Environment Description
    flower falling petals 落花
    petal 花瓣 cherry_blossoms 樱花
    rose 玫瑰 forest 森林/树
    rose petals 玫瑰花瓣 pink four petal flower 粉色四瓣花
  • Building 建筑
    | Environment | Description | Environment | Description |

|—————————–|————-|———————————————————-|————-|
| in the baroque architecture | 巴洛克建筑 | in the romanesque architecture streets | 罗马街道 |
| in the palace | 宫廷 | at the castle | 城外为背景 |
| in the castle | 城内为背景 | in the street | 在街上 |
| in the cyberpunk city | 赛博朋克 | rainy night in a cyberpunk city with glowing neon lights | 赛博朋克雨天霓虹灯 |
| at the lighthouse | 灯塔 | onsen | 温泉 |
| by the moon | 月亮边 | in a bar, in bars | 酒吧 |
| in a tavern | 居酒屋 | Japanese arch | 鸟居 |
| church | 教堂 | in a locker room | 上锁房间里 |
| cityspace | 城市风光式 | power lines | 电力线 |
| building | 建筑 | ruins | 废墟/遗迹 |

References

Prompt Wiki

基础

Circle

Circle 方法允许您绘制完美的圆形。圆形的直径等于宽度和高度之间较小的数字

1
2
3
Circle()
.stroke(Color.black, lineWidth: 2)
.frame(width: 44, height: 44)

Ellipse

Ellipse 就像一个圆,但没有完美的纵横比 1:1。当宽度和高度不同时,它会填满空间并扭曲自己。
Ellipse()
.stroke(Color.black, lineWidth: 2)
.frame(width: 44, height: 88)

Rectangle

虽然 SwiftUI 中的大多数元素(例如 stacks 堆栈、颜色、渐变)都以矩形的形式,但它们不是形状。 Rectangle 具有 shape 属性,你可以进行描边或用作蒙版的用途。

1
2
3
Rectangle()
.foregroundColor(.blue)
.ignoresSafeArea()

RoundedRectangle

RoundedRectangle(圆角矩形) 有 cornerRadius(圆角) 和 style(样式)属性。它非常适合创建按钮、卡片,看起来更美观和圆滑。

1
2
3
4
RoundedRectangle(cornerRadius: 30, style: .continuous)
.fill(Color.green)
.frame(height: 44)
.overlay(Text("Sign up").bold())

Capsule

与 RoundedRectangle 类似,Capsule 类似胶囊的形状。胶囊的每一端都由一个半圆组成。您可以将它们用于按钮的绘制。

1
2
3
4
Capsule()
.fill(Color.green)
.frame(height: 44)
.overlay(Text("Sign up").bold())

实践

xPCQdD

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
import SwiftUI

struct ContentView: View {
var body: some View {
ZStack {
Rectangle()
.fill(Color.blue).ignoresSafeArea()

VStack {
Circle()
.stroke(Color.black, lineWidth: 2)
.frame(width: 44, height: 44)
Text("Hong jun yao").foregroundColor(Color.red).bold()
Capsule()
.foregroundColor(Color.green)
.frame(height: 44)
.overlay(Text("Sign up"))
}
.padding()
.background(Color.white)
.clipShape(RoundedRectangle(cornerRadius: 25.0, style: .continuous))
.padding()
}
.frame(width: 300.0, height: 500.0)
}
}

struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}

SwiftUI 中的 Stacks 类似于 UIKit 中的 stack views。通过组合水平和垂直的方式排列视图构建更复杂的应用界面。Stacks 有 3 种类型:HStack、VStack 和 ZStack。

VStack

VFyRLT

可以通过 VStack 从上到下垂直堆叠视图,同时我们可以进一步添加alignment(对齐方式)或间距(spacing)来进一步自定义视图。

1
2
3
4
5
6
VStack(alignment: .leading, spacing: 16) {
Text("Hello, world!")
.font(.title)
Spacer()
Text("Second line")
}

HStack

CE5YPH
HStack 用于水平堆叠视图。就像 VStack 一样,您可以设置对齐方式和间距进一步自定义视图

1
2
3
4
5
6
HStack(alignment: .bottom, spacing: 16) {
Text("Hello, world!")
.font(.title)
Spacer()
Text("Second line")
}

ZStack

zPp77c
ZStack 类似设计软件的层概念,元素都是在一个视图上进行堆叠的,类似在三维立体空间堆叠视图,由于元素可以相互浮动,因此 ZStack 的对齐方式会将所有项目移到一个位置。

1
2
3
4
5
6
7
8
9
10
ZStack(alignment: .topLeading) {
Rectangle()
.foregroundColor(.blue)
Text("Hello, world!")
.font(.title)
Spacer()
Text("Second line")
}
.padding()
.frame(width: 320)

在前面的文章我已用过@State属性,使用@State修饰某个属性后,SwiftUI将会把该属性存储到一个特殊的内存区域内,并且这个区域和View struct是隔离的;
当@State修饰的属性的值发生变化后,SwiftUI会根据该属性重新绘制视图;

在开发中,我们需要把一个View的属性,传递到一个子View中;
Swift中,值传递的形式是值传递,也就是说,传个子View的是值的拷贝;子视图对这个值进行了修改后,不会影响父视图;
使用@Binding修饰后,属性就变成了一个引用类型,这样子视图对值进行了修改后,父视图中的值也会发生变化

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
struct customButton:View {
@Binding var tapCount:Int
var body: some View {
Button {
self.tapCount += 1

} label: {
Text("Hello World 第\(tapCount)次点击")
} //渲染颜色
.tint(.purple)
// 按钮样式 .bordered、.borderless 和 .plain
.buttonStyle(.bordered)
//按钮边框样式
.buttonBorderShape(.capsule)
//按钮预设大小
.controlSize(.large)
}
}

struct ContentView: View {
@State private var tapCount = 0
var body: some View {

VStack{
customButton(tapCount: $tapCount)
}
}
}

我们看到我们将tapCount 作为参数传入customButton中,当customButton这个subview内进行点击修改的时候,我们的parentView也会随着变化。

在我之前@State研究中我们探讨过@State,通过它,我们可以方便的将值类型数据作为View的Source of truth(单一数据源)。在SwiftUI 1.0时代,如果想将引用类型作为source of truth,通常的方法是使用@EnvironmentObject或者 @ObservedObject。

@StateObject 是在 SwiftUI 2.0 中才添加的属性包装器,它的出现解决了在某些情况下使用 @ObservedObject 视图会出现超预期的问题

示例:
user类

1
2
3
class User: ObservableObject {
var username = "@twostraws"
}

如果要在各种视图中使用它,则需要在 SwiftUI 外部创建它并将其注入,或者在其中一个 SwiftUI 视图中创建它并使用 @StateObject,如下所示:

1
2
3
4
5
6
7
struct ContentView: View {
@StateObject var user = User()

var body: some View {
Text("Username: \(user.username)")
}
}

这将确保视图更新时不会破坏 User 实例

以前,可能曾经使用 @ObservedObject 来获得相同的结果,但这很危险–有时且仅在某些情况下,@ObservedObject 可能会意外释放其存储的对象,因为它并不是被设计为最终的真理来源。 目的。 @StateObject 不会发生这种情况,因此应该改用它。

推荐阅读

@StateObject 和 @ObservedObject 的区别和使用

安裝环境

1
2
3
4
5
6
7
8
9
brew install cmake protobuf rust git wget

# 使用 brew 安裝
brew install python@3.10

# 使用 pyenv 安裝
pyenv install 3.10.6
# 啟動 3.10.6
pyenv local 3.10.6

初始化 Stable Diffusion WebUI

1
2
3
git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui
cd stable-diffusion-webui
./webui.sh

Stable Diffusion之模型篇

背景

4AxA4q

如上图,是我们各个业务系统进行SSO登录的流程,我们之前已经通过OIDC搭建之Ory Hydra 2.0实践,进行了登录流程的构建,那么本次我们进行一下登出流程的实践

首先我们的登出需求分为以下几种:

  • 1、所有应用统一登出: 账号在 pc1:admin、wms pc2:admin、pms 全部退出

  • 2、单应用统一登出: 账号在 pc1:admin pc2:admin 退出

  • 3、单token登出: 账号在 pc1:admin 退出,pc2:admin 不退出 (仅支持业务系统实现)

最终取决于 this.hydraAdminService.revokeOAuth2ConsentSessions的参数,具体实现如下

实现方式

业务系统 实现

在各个应用端添加退出接口

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
// 手工logout
async logout(user) {
const access_token = user.access_token
const subject = user.mongo_id
const client_id = user.app.client_id

// 清除 login session
const { data: revokeOAuth2LoginSessions } = await this.hydraAdminService.revokeOAuth2LoginSessions({ subject: subject })
console.log("revokeOAuth2LoginSessions", revokeOAuth2LoginSessions)

// 所有应用或单应用登出,清除 consent session 注销所有token
// 通过client单应用登录后通过all全应用退出。
const { data: revokeOAuth2ConsentSessions } = await this.hydraAdminService.revokeOAuth2ConsentSessions({ subject: subject, client: client_id, all: false, })
console.log("revokeOAuth2ConsentSessions", revokeOAuth2ConsentSessions)

// 单token登出:只注销当前token
// const headers = { 'Authorization': `Basic ${Buffer.from(`${this.config.get('app').client_id}:${this.config.get('app').client_secret}`).toString('base64')}` }
// console.log("headers", headers)
// const revokeOAuth2Token = await this.hydraPublicService.revokeOAuth2Token({ token: access_token }, { headers: headers })
// console.log("revokeOAuth2Token", revokeOAuth2Token)
// return
}

统一授权认证中心 实现

86IxXC

  • 要求
    登出链接:http://oauth2.dev.dakewe.com/oauth2/sessions/logout?id_token_hint=XXX

可选参数,id_token_hint其实是用来找到你对应的应用。建议都传
可选参数post_logout_redirect_uris,如需要退出后,返回业务系统。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
async getLogout(dto: GetLogoutDto) {
const logout_challenge = dto.logout_challenge
try {
const { data: getLogoutRequest } =
await this.hydraAdminService.getOAuth2LogoutRequest({ logoutChallenge: logout_challenge })
console.log('getLogoutRequest', getLogoutRequest)
return getLogoutRequest
} catch (error) {
if (error.isAxiosError) {
console.log(error.response)
throw new HttpException(`${error.response.data.error},${error.response.data.error_description}`, error.response.status);
} else {
throw new HttpException(error, 500);
}
}
}

async acceptLogout(acceptLogout: AcceptLogoutDto) {
const { logout_challenge, is_all = false } = acceptLogout
console.log("接受退出流程")
let getOAuth2LogoutRequest
try {
const { data: data } =
await this.hydraAdminService.getOAuth2LogoutRequest({ logoutChallenge: logout_challenge })
getOAuth2LogoutRequest = data
} catch (error) {
if (error.isAxiosError) {
console.log(error.response)
throw new HttpException(`${error.response.data.error},${error.response.data.error_description}`, error.response.status);
} else {
throw new HttpException(error, 500);
}
}
console.log('getOAuth2LogoutRequest', getOAuth2LogoutRequest)
try {
const subject = getOAuth2LogoutRequest.subject
const client = getOAuth2LogoutRequest.client
console.log('-------client_id', client?.client_id)
console.log('-------subject', subject)
// 清楚 logout session
const { data: acceptLogoutRequest } =
await this.hydraAdminService.acceptOAuth2LogoutRequest({ logoutChallenge: logout_challenge })
console.log('acceptLogoutRequest', acceptLogoutRequest)
// 清除 consent session 注销所有token
const { data: revokeOAuth2ConsentSessions } = await this.hydraAdminService.revokeOAuth2ConsentSessions({ subject: subject, client: client && is_all === false ? client.client_id : undefined, all: is_all, })
console.log("revokeOAuth2ConsentSessions", revokeOAuth2ConsentSessions)

return acceptLogoutRequest.redirect_to
} catch (error) {
if (error.isAxiosError) {
console.log(error.response)
throw new HttpException(`${error.response.data.error},${error.response.data.error_description}`, error.response.status);
} else {
throw new HttpException(error, 500);
}
}
}

相关链接

Implementing the OIDC logout endpoint & UI
Logout logic diagram

看着15年的swift笔记,想当初自己也是一名swifter呢,今天正式回归到swift开发,完成一个桌面端的AI产品。当前swift已经使用swiftUI了,那么就从swiftUI重新开始吧

SwiftUI 提供了许多属性包装器,可用于更新/观察数据和重新加载视图。这些属性包装器为视图和可变数据之间的交互提供了多种方式。为了在 SwiftUI 中构建一个很棒的应用程序,对这些包装器有一个清晰的理解非常重要。

@State 基础

@State 是一个简单的属性,应该只用于整数、字符串、布尔值等原始类型。@State 包装器是更新 视图变量状态的最简单方法。如果我们在带有 @State 属性包装器的视图中创建一个属性,SwiftUI 会以不同的方式管理该属性的内存。只要视图存在,它就会将变量的值保留在内存中。每当状态发生更改时,SwiftUI 会自动使用更新的信息重新加载视图。

示例

确保使用@State 的对象属于单个视图,并且它们被标记为私有。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
import SwiftUI
struct ContentView: View {
@State private var num: Int = 0
@State private var isIncreasing: Bool = false
var body: some View {
HStack {
Button(action: {
num -= 1
isIncreasing = false
}, label: {
Text("-")
})
.frame(width: 10, height: 10)
Text(isIncreasing ? "增加 to \(num)" : "减小 to \(num)")
.foregroundColor(.black)
Button(action: {
num += 1
isIncreasing = true
}, label: {
Text("+")
})
.frame(width: 12, height: 10)
}
}
}

在上面的例子中,有两个按钮’ + ‘和’-‘,分别增加和减少’ num ‘变量的值。状态变量 (num) 存储其先前的值并根据其状态更新视图。

简单理解就是 属性状态发生变化是,会自动更新UI

在有状态的流处理中,当开发人员启用了 Flink 中的 checkpoint 机制,那么状态将会持久化以防止数据的丢失并确保发生故障时能够完全恢复。选择何种状态后端,将决定状态持久化的方式和位置。

Flink 提供了三种可用的状态后端:MemoryStateBackendFsStateBackend,和RocksDBStateBackend

IAXXfM

MemoryStateBackend

MemoryStateBackend 是将状态维护在 Java 堆上的一个内部状态后端。键值状态和窗口算子使用哈希表来存储数据(values)和定时器(timers)。当应用程序 checkpoint 时,此后端会在将状态发给 JobManager 之前快照下状态,JobManager 也将状态存储在 Java 堆上。默认情况下,MemoryStateBackend 配置成支持异步快照。异步快照可以避免阻塞数据流的处理,从而避免反压的发生。

使用 MemoryStateBackend 时的注意点:

  • 默认情况下,每一个状态的大小限制为 5 MB。可以通过 MemoryStateBackend 的构造函数增加这个大小。

  • 状态大小受到 akka 帧大小的限制,所以无论怎么调整状态大小配置,都不能大于 akka 的帧大小。也可以通过 akka.framesize 调整 akka 帧大小(通过配置文档了解更多)。

  • 状态的总大小不能超过 JobManager 的内存。
    何时使用 MemoryStateBackend:

  • 本地开发或调试时建议使用 MemoryStateBackend,因为这种场景的状态大小的是有限的。

  • MemoryStateBackend 最适合小状态的应用场景。例如 Kafka consumer,或者一次仅一记录的函数 (Map, FlatMap,或 Filter)。

FsStateBackend

FsStateBackend 需要配置的主要是文件系统,如 URL(类型,地址,路径)。举个例子,比如可以是:

  • “hdfs://namenode:40010/flink/checkpoints” 或
  • “s3://flink/checkpoints”
    当选择使用 FsStateBackend 时,正在进行的数据会被存在 TaskManager 的内存中。在 checkpoint 时,此后端会将状态快照写入配置的文件系统和目录的文件中,同时会在 JobManager 的内存中(在高可用场景下会存在 Zookeeper 中)存储极少的元数据。

默认情况下,FsStateBackend 配置成提供异步快照,以避免在状态 checkpoint 时阻塞数据流的处理。该特性可以实例化 FsStateBackend 时传入 false 的布尔标志来禁用掉,例如:

1
new FsStateBackend(path, false);

使用 FsStateBackend 时的注意点:

  • 当前的状态仍然会先存在 TaskManager 中,所以状态的大小不能超过 TaskManager 的内存。
    何时使用 FsStateBackend:

  • FsStateBackend 适用于处理大状态,长窗口,或大键值状态的有状态处理任务。

  • FsStateBackend 非常适合用于高可用方案。

RocksDBStateBackend

RocksDBStateBackend 的配置也需要一个文件系统(类型,地址,路径),如下所示:

  • “hdfs://namenode:40010/flink/checkpoints” 或
  • “s3://flink/checkpoints”
    RocksDB 是一种嵌入式的本地数据库。RocksDBStateBackend 将处理中的数据使用 RocksDB 存储在本地磁盘上。在 checkpoint 时,整个 RocksDB 数据库会被存储到配置的文件系统中,或者在超大状态作业时可以将增量的数据存储到配置的文件系统中。同时 Flink 会将极少的元数据存储在 JobManager 的内存中,或者在 Zookeeper 中(对于高可用的情况)。RocksDB 默认也是配置成异步快照的模式。

使用 RocksDBStateBackend 时的注意点:

  • RocksDB 支持的单 key 和单 value 的大小最大为每个 2^31 字节。这是因为 RocksDB 的 JNI API 是基于 byte[] 的。

  • 我们需要强调的是,对于使用具有合并操作的状态的应用程序,例如 ListState,随着时间可能会累积到超过 2^31 字节大小,这将会导致在接下来的查询中失败。
    何时使用 RocksDBStateBackend:

  • RocksDBStateBackend 最适合用于处理大状态,长窗口,或大键值状态的有状态处理任务。

  • RocksDBStateBackend 非常适合用于高可用方案。

  • RocksDBStateBackend 是目前唯一支持增量 checkpoint 的后端。增量 checkpoint 非常使用于超大状态的场景。
    当使用 RocksDB 时,状态大小只受限于磁盘可用空间的大小。这也使得 RocksDBStateBackend 成为管理超大状态的最佳选择。使用 RocksDB 的权衡点在于所有的状态相关的操作都需要序列化(或反序列化)才能跨越 JNI 边界。与上面提到的堆上后端相比,这可能会影响应用程序的吞吐量。

不同状态后端满足不同场景的需求,在开始开发应用程序之前应该仔细考虑和规划后选择。这可确保选择了正确的状态后端以最好地满足应用程序和业务需求。

背景

UDF 实现的几种方式

udf 提供 5 种自定义方式,在实际业务中,我们根据业务需求继承对应的 Function,并实现对应的方法。

  • 标量函数 将标量值转换成一个新标量值;简单理解就是 一对一模式,比如输入一个身份证号码,输出一个加密的字符串,实现(ScalarFunction),重写 eval() 方法。

  • 表值函数 将标量值转换成新的行数据;简单理解就是一对多模式,比如一个字段存储为 逗号隔开的字符串,可通过(TableFunction)进行 split,输出多条数据。

  • 聚合函数 将多行数据里的标量值转换成一个新标量值; 多对一模式,通过聚合操作把多行输出为一个值。(AggregateFunction)

  • 表聚合函数将多行的标量值映射到新行。

  • 异步表函数是用于执行查找的表源的特殊函数。

以下主要介绍标量(Scalar)UDF的实现

实践:截取字符串

实现自定义的 UDF 功能主要分为以下几个步骤:

1、自定义 UDF 函数的实现逻辑,打包成 jar 包
2、上传 jar 包 到 flink 工程的 lib 目录下
3、使用 Flink 中的 SQL API 直接进行使用

1、自定义 UDF 函数

  • 创建 maven 工程 ,工程需要引用以下pom 依赖

    1
    2
    3
    4
    5
    6
    <dependency>
      <groupId>org.apache.flink</groupId>
      <artifactId>flink-table-common</artifactId>
      <version>${flink.version}</version>
      <scope>provided</scope>
    </dependency>
  • 定义一个对字符串进行截取的函数,比如 5个字符截取1到 3位的字符

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    package org.example;
    import org.apache.flink.table.functions.ScalarFunction;
    /**
    * classname SubstringFunction
    * description 标量函数
    */
    public class SubstringFunction extends ScalarFunction {
    public String eval(String s, Integer begin, Integer end) {
    return s.substring(begin, end);
    }
    }

  • 使用 maven 进行打包

    1
    mvn clean packagen

我是使用streamPark,直接上传jar包即可

tbrmMR

3、使用

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
CREATE TABLE products(
  id INT,
  name STRING,
  description STRING,
  PRIMARY KEY (id) NOT ENFORCED
) WITH (
  'connector' = 'jdbc',
  'url' = 'jdbc:mysql://127.0.0.1:3306/demo',
  'username' = 'root',
  'password' = '123456',
  'table-name' = 'products'
);
//创建 function 先需要声明函数
CREATE FUNCTION SubstringFunction as 'org.example.SubstringFunction';
//使用
SELECT id,name,SubstringFunction(name,1,3) AS substr from products;

相关链接

示例

0%