Skip to content

Commit

Permalink
fix(typescript): add correct type safety to zone#create (#307)
Browse files Browse the repository at this point in the history
  • Loading branch information
callmehiphop authored and bcoe committed Oct 16, 2019
1 parent a526329 commit 6591bbc
Show file tree
Hide file tree
Showing 2 changed files with 43 additions and 4 deletions.
1 change: 1 addition & 0 deletions packages/google-cloud-dns/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ export interface CreateZoneRequest {
}

export type CreateZoneResponse = [Zone, Metadata];
export type CreateZoneCallback = GetZoneCallback;

export interface DNSOptions extends GoogleAuthOptions {
/**
Expand Down
46 changes: 42 additions & 4 deletions packages/google-cloud-dns/src/zone.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import {
GetConfig,
Metadata,
ServiceObject,
ServiceObjectConfig,
} from '@google-cloud/common';
import {paginator} from '@google-cloud/paginator';
import {promisifyAll} from '@google-cloud/promisify';
Expand All @@ -30,7 +31,12 @@ const zonefile = require('dns-zonefile');

import {Change, CreateChangeCallback, CreateChangeRequest} from './change';
import {Record, RecordMetadata, RecordObject} from './record';
import {DNS, CreateZoneRequest} from '.';
import {
DNS,
CreateZoneRequest,
CreateZoneResponse,
CreateZoneCallback,
} from '.';
import {Readable} from 'stream';
import {InstanceResponseCallback} from '@google-cloud/common';
import {GetResponse} from '@google-cloud/common/build/src/service-object';
Expand Down Expand Up @@ -166,6 +172,26 @@ export interface ZoneExportCallback {
(err: Error | null): void;
}

// This type essentially just clones a class but allows us to exclude methods
// from the type itself. In this case it is useful because we want to override
// the Zone#create signature that is defined in the common library.
type Without<T, K> = {
[P in Exclude<keyof T, K>]: T[P];
};

// Using the Without type, we essentially make a new ServiceObject type that
// doesn't contain any of the methods that have signatures we wish to override.
type ZoneServiceObject = new (config: ServiceObjectConfig) => Without<
ServiceObject<Zone>,
'create' | 'delete' | 'get'
>;

// This is used purely for making TypeScript think that the object we are
// subclassing does not contain a signature mismatch for methods we are
// overriding.
// tslint:disable-next-line variable-name
const ZoneServiceObject = ServiceObject as ZoneServiceObject;

/**
* A Zone object is used to interact with your project's managed zone. It will
* help you add or delete records, delete your zone, and many other convenience
Expand All @@ -179,7 +205,7 @@ export interface ZoneExportCallback {
*
* const zone = dns.zone('zone-id');
*/
class Zone extends ServiceObject<Zone> {
class Zone extends ZoneServiceObject {
name: string;
getRecordsStream: (query?: GetRecordsRequest | string | string[]) => Readable;
getChangesStream: (query?: GetChangesRequest) => Readable;
Expand Down Expand Up @@ -358,6 +384,17 @@ class Zone extends ServiceObject<Zone> {
this.getChangesStream = paginator.streamify('getChanges');
}

create(config: CreateZoneRequest): Promise<CreateZoneResponse>;
create(config: CreateZoneRequest, callback: CreateZoneCallback): void;
create(
config: CreateZoneRequest,
callback?: CreateZoneCallback
): void | Promise<CreateZoneResponse> {
// tslint:disable-next-line no-any
const args = [config, callback!] as any;
ServiceObject.prototype.create.apply(this, args);
}

get(config?: GetZoneRequest): Promise<GetResponse<Zone>>;
get(callback: InstanceResponseCallback<Zone>): void;
get(config: GetZoneRequest, callback: InstanceResponseCallback<Zone>): void;
Expand All @@ -368,7 +405,7 @@ class Zone extends ServiceObject<Zone> {
const config = typeof configOrCallback === 'object' ? configOrCallback : {};
callback =
typeof configOrCallback === 'function' ? configOrCallback : callback;
super.get(config, callback!);
ServiceObject.prototype.get.call(this, config, callback!);
}

addRecords(records: Record | Record[]): Promise<CreateChangeResponse>;
Expand Down Expand Up @@ -579,7 +616,8 @@ class Zone extends ServiceObject<Zone> {
});
return;
}
super.delete(callback!);

ServiceObject.prototype.delete.call(this, callback!);
}

deleteRecords(
Expand Down

0 comments on commit 6591bbc

Please sign in to comment.