gpt4 book ai didi

angularjs - 如何做正确的存储库工厂?

转载 作者:搜寻专家 更新时间:2023-10-30 21:00:26 26 4
gpt4 key购买 nike

我在项目之间有一些空闲时间,所以我决定学习 typescript。因此我想做一个存储库工厂。这个想法很简单,有一些 API 我可以在其中访问 models crud 操作。拥有一个用于商业模型的 generic repository 是很好的解决方案。但仍然从 CRUD 方法中获取 model 类。

正确的做法是什么?有人可以帮我解决这个问题吗?如何正确执行?

我想要实现的是:

var factory = new RepositoryFactory($resource, 'http://api.com');
var repo = factory.getRepository(User);
var user = repo.getAll();

我开始做这样的事情:

IEntity:

'use strict';

export interface IEntity {
id: number;
}

IRepository:

'use strict';

import {IEntity} from "./IEntity";

export interface IRepository<T extends IEntity> {
getAll(params:Object): T[];
getById(id:number): T;
create(data:Object): T;
update(id:number, data:{id:number}): T;
remove(id:number): boolean;
}

RepositoryFactory

'use strict';

import {IEntity} from "./IEntity";
import {Repository} from "./Repository";

export default class RepositoryFactory {
protected $resource:any;
protected url:string;

constructor($resource:any, url:string) {
this.$resource = $resource;
this.url = url;
}

public getRepository<T extends IEntity>(model:T):Repository {
return new Repository(this.$resource, this.url, model)
}
}

`Repository`:
'use strict';

import {IRepository} from "./IRepository";
import {IEntity} from "./IEntity";

export default class Repository<T extends IEntity> implements IRepository<T> {
protected $resource:any;
protected resource:any;
protected url:string;
protected model:T;

constructor($resource:any, url:string, model:T) {
this.$resource = $resource;
this.url = url;
this.model = model;
this.resource = this.getResource(model.path);
}

getAll(params:Object):T[] {
let results = this.resource.query((typeof params === 'undefined' ? {} : params), this.onSuccess);

return this.returnPromise(results);
}

getById(id:number):T {
let model = this.resource.get({id: id}, this.onSuccess);

return this.returnPromise(model);
}

create(data:Object):T {
let model = new this.resource(data);

return model.$save().then(this.onSuccess);
}

update(id:number, data:Object):T {
data.id = id;
var model = new this.resource(data);

return model.$update().then(this.onSuccess);
}

remove(id:number):boolean {
var data = {id: id};
var model = new this.resource(data);

return model.$delete().then(this.onSuccess);
}

protected getResource(path:string) {
return this.$resource(this.url + path, {id: '@id'}, {
'update': {
method: 'PUT'
},
'get': {
method: 'GET'
},
'save': {
method: 'POST'
},
'query': {
method: 'GET'
},
'remove': {
method: 'DELETE'
},
'delete': {
method: 'DELETE'
}
});
}

protected onSuccess(response:any) {
if (this.checkPropertyExistence(response, 'data')) {
if (response.data instanceof Array) {
let results = response.data;
for (var key in results) {
if (results.hasOwnProperty(key)) {
results[key] = new this.model(results[key]);
}
}

return results;
} else {
return new this.model(response.data);
}
}

return response;
}

protected transformRequest(obj:Object) {
var str = [];
for (var p in obj) {
if (obj.hasOwnProperty(p)) {
str.push(encodeURIComponent(p) + "=" + encodeURIComponent(obj[p]));
}
}

return str.join("&");
}

protected returnPromise(object:Object) {
return object.$promise.then(function (result) {
return result;
});
}

protected checkPropertyExistence(obj:Object, paths:string|string[]) {
for (var i = 0; i < paths.length; i++) {
if (!obj || !obj.hasOwnProperty(paths[i])) {
return false;
}
obj = obj[paths[i]];
}
return true;
}
}

用户:

'use strict';

import {IEntity} from "./IEntity";

export default class User implements IEntity {
id:number;
name:string;

static _path:string = '/users';

constructor(id:number, name:string) {
this.id = id;
this.name = name;
}

static get path():string {
return this._path;
}
}

最佳答案

嘿伙计们,我设法为你们创建了工作示例。该示例展示了如何使用 typescript 创建存储库工厂。

我准备了这个DEMO FIDDLE点击右侧的RUN,会出现单按钮页面。单击按钮后 console.log 将显示 getAll 方法 results

在示例中,我模拟了数据,只是为了表明工厂正常工作。如果有人想改进它,请随意并欢迎这样做!

它是如何工作的?

//create factory, you can do it in an abstract controller class
//and later extends controller by it so you can easy get access to repository
var factory = new RepositoryFactory();
//inject path for $resource (unused in example)
//and your model.entity namespace
var repo = factory.getRepository('/users', 'User');

//call repo method
var users = repo.getAll({});

当使用 Angular 时,创建 RepositoryFactory 作为 service。就这样。您可能还想注入(inject) $resource 以从 API 获取正确的数据。

这是一个完整的示例代码:

interface IEntity {
id: number;
}

class Entity implements IEntity {
private _id:number;
private _name:string;
private _birth:Date;

constructor(parameters: {id:number, name:string, birth:Date}) {
this._id = parameters.id;
this._name = parameters.name;
this._birth = parameters.birth;
}

get id():number {
return this._id;
}

set id(value:number) {
this._id = value;
}

get name():string {
return this._name;
}

set name(value:string) {
this._name = value;
}

get birth():Date {
return this._birth;
}

set birth(value:Date) {
this._birth = value;
}
}

class RepositoryFactory {
public getRepository<T extends IEntity>(path:string, model:string):IRepository<T> {
return new Repository<T>(path, model)
}
}

interface IRepository<T extends IEntity> {
getAll(params:Object): T[];
getById(id:number): T;
create(data:Object): T;
update(id:number, data:{id:number}): T;
remove(id:number): boolean;
}

class Repository<T extends IEntity> implements IRepository<T> {
protected path:string;
protected model:string;

constructor(path:string, model:string) {
this.path = path;
this.model = model;
}

getAll(params:Object):T[] {
let results = [
{id:1, name: 'rafal', birth:new Date()},
{id:2, name: 'szymon', birth:new Date()},
{id:3, name: 'mateusz', birth:new Date()},
];

let entities= [];
for (var key in results) {
if (results.hasOwnProperty(key)) {
let entity = Object.create(window[this.model].prototype);
entity.constructor.apply(entity, new Array(results[key]));
entities.push(entity);
}
}

return entities;
}

getById(id:number):T {
let object = {id:id, name: 'test', birth:new Date()};

var entity = Object.create(window[this.model].prototype);
entity.constructor.apply(entity, new Array(object));

return entity;
}

create(data:Object):T {
var entity = Object.create(window[this.model].prototype);
entity.constructor.apply(entity, new Array(data));

return entity;
}

update(id:number, data:Object):T {
var entity = Object.create(window[this.model].prototype);
entity.constructor.apply(entity, new Array(data));

return entity;
}

remove(id:number):boolean {
return true;
}
}

var factory = new RepositoryFactory();
var repo = factory.getRepository('/users', 'Entity');

var users = repo.getAll({});

关于angularjs - 如何做正确的存储库工厂?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35552942/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com