typescript - Hva er god praksis når det gjelder modeller i Angular?
Jeg vil gjerne vise en vaskemaskin i Angular-appen min. For å gjøre det, laget jeg en Machine-modell:
import { User } from './user.model';
export class Machine {
id: number;
type: string;
pricing: string;
enableDurationSelection: boolean;
maxDuration: number;
costPerCycle: number;
elapsedTime?: number = 0;
user?: User;
}
og en maskinbruker:
export class User {
id: number;
firstName?: string;
lastName: string;
balance: number;
getUsername(): string {
let username = '';
if (this.firstName) {
username += this.firstName[0] + '. ';
}
username += this.lastName.toUpperCase();
return username;
}
}
Hvordan kan jeg utføre duck typing for
User-modellen?getUsername()-egenskapen ser ut til å ødelegge det.Jeg vil gjerne legge til en timer på maskinen for å vise varigheten av en syklus. Jeg kunne legge til
startTimer()ogstopTimer()egenskaper i minMachine-modell, men det trenger også ekstra egenskaper som enObserversom ikke er relatert til maskindataene og som også vil ødelegge duck typing.
Hva er den anbefalte måten å håndtere denne situasjonen på?
Rediger
Endelig fant jeg klasse-transformer-pakken på NPM for å gjøre det.
Svar #1
Det ser ut som du vil opprette objektinstanser ved å bruke objektnotasjon med alle feltene, og du antar at metoder på en eller annen måte bør legges til det opprettede objektet.
Det nærmeste alternativet ville være å legge til en konstruktør i klassen som aksepterer et objekt som inneholder startverdier for feltene:
interface MachineOptions {
id : number;
type: string;
...
}
export class WashingMachine {
// field declarations here
public constructor(options: MachineOptions) {
// copy options to instance's fields here
}
}
const machine = new WashingMachine({
id: 1,
type: 'm-type1',
...
})
Jeg foreslår også å unngå å bruke klassen som grensesnittimplementering her (som class WashingMachine : IMachineOptions) slik at du kan skjule implementasjonsdetaljer (intern feltssemantikk kan avvike fra alternativer).
OPPD: hvis du vil få et ferdiglaget maskinobjekt fra en nett-API-tjeneste, kan du pakke inn svaret fra en server et sted i den tjenesten:
class MachineService {
getMachine(id: number): Observable<WashingMachine> {
return this.http
.get(`/machine/${id}`) // edit the API call as needed
.pipe(map(options => new WashingMachine(options)); // wrapping part
}
}
class MachineComponent {
...
ngOnInit() {
// Example of usage
this.machineService
.getMachine(1)
.subscribe(m => m.startTimer());
}
}
