Aws Cognito 自定义授权流程
概要
原来有个网站,存在完善的账号管理,现在要增加一个网站,希望能使用统一的账号管理。
理想的方案是增加一个OAuth2服务,两个网站分别接入这个服务。但是由于特别的原因,旧网站只能进行微小的发动,于是要求这个 OAuth2 要能够支持自定义流程以旧网站的顺利接入而且不需要多少的变化。最终选择了使用 AWS Cognito 服务
原来有个网站,存在完善的账号管理,现在要增加一个网站,希望能使用统一的账号管理。
理想的方案是增加一个OAuth2服务,两个网站分别接入这个服务。但是由于特别的原因,旧网站只能进行微小的发动,于是要求这个 OAuth2 要能够支持自定义流程以旧网站的顺利接入而且不需要多少的变化。最终选择了使用 AWS Cognito 服务
ResourceCollection 是用于处理 返回值为json的时候定义返回的集合的格式,集合内的单个元素可以使用 Illuminate\Http\Resources\Json\JsonResource 定义,或者直接在toArray中重新定义。
use App\User;
use App\Http\Resources\User as UserResource;
Route::get('/user', function () {
return UserResource::collection(User::all());
});
// 如果定义了Collection
namespace App\Http\Resources;
use Illuminate\Http\Resources\Json\ResourceCollection;
class UserCollection extends ResourceCollection
{
/**
* Transform the resource collection into an array.
*
* @param \Illuminate\Http\Request $request
* @return array
*/
public function toArray($request)
{
return [
'data' => $this->collection,
'links' => [
'self' => 'link-value',
],
];
}
}
// 新的写法
use App\User;
use App\Http\Resources\UserCollection;
Route::get('/users', function () {
return new UserCollection(User::all());
});
外键需要允许为空(nullable)否则会报错(已经提交issue截止目前未修复)
// tables
Schema::create('users', function (Blueprint $table) {
$table->uuid('id');
$table->string('email', 64)->unique();
$table->boolean('revoked')->default(0);
$table->dateTime('email_verified_at')->nullable();
$table->string('password');
$table->rememberToken();
$table->timestamps();
});
Schema::create('profiles', function (Blueprint $table) {
$table->increments('id');
$table->uuid('user_id')->nullable()->index(); // 目前需要为 nullable, 这个bug目前为止还没有修复
$table->string('name');
$table->string('description')->nullable();
$table->timestamps();
});
class Teacher extends Model
{
protected $guarded=[];
//
public function user() {
return $this->belongsTo(User::class, 'user_id', 'id'); // 这里必须填写,虽然Laravel 虽然在Laravel 中默认就是这些值,但是Laravel-Admin 没办法获取到默认的字段名
}
}
// Model
class User extends Authenticatable
{
use Notifiable;
public $incrementing=false;
/**
* The attributes that should be hidden for arrays.
*
* @var array
*/
protected $hidden = [
'password', 'remember_token',
];
public function profile() {
return $this->hasOne(Profile::class);
}
}
// Form
$form = new Form(new Profile);
$form->text('name', '姓名')->rules('required');
$form->password('user.email', '密码')->rules('required');
$form->password('user.password', '密码')->rules('required');
$form->textarea('description', '描述');
//
主键必须为自动生成,否则不能正确的保存从表
tables
CREATE TABLE `main` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `sub` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT, // 非自动生成主键不能正确的保存
`key` int(10) varchar(100) NOT NULL,
`main_id` int(10) unsigned NOT NULL,
`value` varchar(255) NOT NULL,
PRIMARY KEY (`id`),
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
Models
class Main extends Model
{
public $timestamps = false;
public function subs()
{
return $this->hasMany(Sub::class, 'main_id'); // main_id 必须填写,虽然 Laravel 单独使用的时候可以不用写
}
}
class Sub extends Model
{
public $timestamps = false;
// public $incrementing = false; // 如果没有自动生成的主键而是 key 做为主键的话,会导表单中Sub保存失败,key 为空
// public $primaryKey = 'key';
protected $fillable = ['key', 'value'];
public function main()
{
return $this->belongsTo(Main::class, 'main_id'); //同上
}
}
Form
$form = new Form(new Main);
$form->text('name', '名称');
$form->hasMany('subs','从表', function (Form\NestedForm $form) {
$form->text('key');
$form->text('value');
});
return $form;
Laravel-admin 完全不适合使用于生产环境,复杂的关系还没有完善
Good at all simple business, not dependent on the server, can be used with API-Gateway.
Only need sample functions.
first of all, we need a AWS account.
launch AWS Console
goto Lambda->Dashbord click the button Create function
enter a name for this function
create a new role for this function.
select Runtime as Nodejs 8.10 (this only nodejs code)
see: Lamda Functions
see: Using an IAM Role
The module-name.export value in your function. For example, "index.handler" would call exports.handler in index.js.