Skip to content

Commit 7e8c915

Browse files
committed
feat: add unwrapData request option
1 parent 7b045e1 commit 7e8c915

File tree

5 files changed

+121
-44
lines changed

5 files changed

+121
-44
lines changed

nodejs/jest.config.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ const customJestConfig: JestConfigWithTsJest = {
55
testEnvironment: "node",
66
transformIgnorePatterns: ["<rootDir>/node_modules/"],
77
extensionsToTreatAsEsm: [".ts"],
8+
setupFiles: ["dotenv/config"],
89
}
910

1011
export default customJestConfig

nodejs/package-lock.json

Lines changed: 16 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

nodejs/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@
3434
"@types/node": "^13.11.1",
3535
"@typescript-eslint/eslint-plugin": "^5.52.0",
3636
"@typescript-eslint/parser": "^5.52.0",
37+
"dotenv": "^16.0.3",
3738
"eslint": "^8.9.0",
3839
"jest": "^29.4.2",
3940
"json-server": "^0.17.1",

nodejs/src/index.ts

Lines changed: 83 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,16 @@
11
import axios, { AxiosInstance, AxiosRequestConfig, AxiosError, AxiosResponse } from 'axios'
2-
import { User, Note, Team, CreateNoteOptions, GetMe, GetUserHistory, GetUserNotes, GetUserNote, CreateUserNote, GetUserTeams, GetTeamNotes, CreateTeamNote, DeleteUserNote, DeleteTeamNote, UpdateUserNote, SingleNote, UpdateTeamNote } from './type'
2+
import { User, Note, Team, CreateNoteOptions, GetMe, GetUserHistory, GetUserNotes, GetUserNote, CreateUserNote, GetUserTeams, GetTeamNotes, CreateTeamNote, SingleNote } from './type'
33
import * as HackMDErrors from './error'
44

5-
export default class API {
5+
export type RequestOptions = {
6+
unwrapData?: boolean
7+
}
8+
9+
const defaultOption: RequestOptions = {
10+
unwrapData: true,
11+
}
12+
13+
export class API {
614
private axios: AxiosInstance
715

816
constructor (readonly accessToken: string, public hackmdAPIEndpointURL: string = "https://api.hackmd.io/v1") {
@@ -53,67 +61,105 @@ export default class API {
5361
)
5462
}
5563

56-
async getMe (): Promise<GetMe> {
57-
const { data } = await this.axios.get<User>("me")
58-
return data
64+
async getMe (option = defaultOption) {
65+
if (option.unwrapData) {
66+
return this.axios.get<User>("me").then(response => response.data) as Promise<GetMe>
67+
} else {
68+
return this.axios.get<GetMe>("me")
69+
}
5970
}
6071

61-
async getHistory (): Promise<GetUserHistory> {
62-
const { data } = await this.axios.get<Note[]>("history")
63-
return data
72+
async getHistory (options = defaultOption) {
73+
if (options.unwrapData) {
74+
return this.axios.get<Note[]>("history").then(response => response.data) as Promise<GetUserHistory>
75+
} else {
76+
return this.axios.get<GetUserHistory>("history")
77+
}
6478
}
6579

66-
async getNoteList (): Promise<GetUserNotes> {
67-
const { data } = await this.axios.get<Note[]>("notes")
68-
return data
80+
async getNoteList (options = defaultOption) {
81+
if (options.unwrapData) {
82+
return this.axios.get<Note[]>("notes").then(response => response.data) as Promise<GetUserNotes>
83+
} else {
84+
return this.axios.get<GetUserNotes>("notes")
85+
}
6986
}
7087

71-
async getNote (noteId: string): Promise<GetUserNote> {
72-
const { data } = await this.axios.get<SingleNote>(`notes/${noteId}`)
73-
return data
88+
async getNote (noteId: string, options = defaultOption) {
89+
if (options.unwrapData) {
90+
return this.axios.get<SingleNote>(`notes/${noteId}`).then(response => response.data) as Promise<GetUserNote>
91+
} else {
92+
return this.axios.get<GetUserNote>(`notes/${noteId}`)
93+
}
7494
}
7595

76-
async createNote (options: CreateNoteOptions): Promise<CreateUserNote> {
77-
const { data } = await this.axios.post<SingleNote>("notes", options)
78-
return data
96+
async createNote (payload: CreateNoteOptions, options = defaultOption) {
97+
if (options.unwrapData) {
98+
return this.axios.post<SingleNote>("notes", payload).then(response => response.data) as Promise<CreateUserNote>
99+
} else {
100+
return this.axios.post<CreateUserNote>("notes", payload)
101+
}
79102
}
80103

81-
async updateNoteContent (noteId: string, content?: string): Promise<UpdateUserNote> {
82-
await this.axios.patch<AxiosResponse>(`notes/${noteId}`, { content })
104+
async updateNoteContent (noteId: string, content?: string, options = defaultOption) {
105+
if (options.unwrapData) {
106+
return this.axios.patch<SingleNote>(`notes/${noteId}`, { content }).then(response => response.data)
107+
} else {
108+
return this.axios.patch<SingleNote>(`notes/${noteId}`, { content })
109+
}
83110
}
84111

85-
async updateNote (noteId: string, options: Partial<Pick<SingleNote, 'content' | 'readPermission' | 'writePermission' | 'permalink'>>): Promise<AxiosResponse> {
86-
return await this.axios.patch<AxiosResponse>(`notes/${noteId}`, options)
112+
async updateNote (noteId: string, payload: Partial<Pick<SingleNote, 'content' | 'readPermission' | 'writePermission' | 'permalink'>>, options = defaultOption) {
113+
if (options.unwrapData) {
114+
return this.axios.patch<SingleNote>(`notes/${noteId}`, payload).then(response => response.data)
115+
} else {
116+
return this.axios.patch<SingleNote>(`notes/${noteId}`, payload)
117+
}
87118
}
88119

89-
async deleteNote (noteId: string): Promise<DeleteUserNote> {
90-
await this.axios.delete<AxiosResponse>(`notes/${noteId}`)
120+
async deleteNote (noteId: string, options = defaultOption) {
121+
if (options.unwrapData) {
122+
return this.axios.delete<SingleNote>(`notes/${noteId}`).then(response => response.data)
123+
} else {
124+
return this.axios.delete<SingleNote>(`notes/${noteId}`)
125+
}
91126
}
92127

93-
async getTeams (): Promise<GetUserTeams> {
94-
const { data } = await this.axios.get<Team[]>("teams")
95-
return data
128+
async getTeams (options = defaultOption) {
129+
if (options.unwrapData) {
130+
return this.axios.get<Team[]>("teams").then(response => response.data) as Promise<GetUserTeams>
131+
} else {
132+
return this.axios.get<GetUserTeams>("teams")
133+
}
96134
}
97135

98-
async getTeamNotes (teamPath: string): Promise<GetTeamNotes> {
99-
const { data } = await this.axios.get<Note[]>(`teams/${teamPath}/notes`)
100-
return data
136+
async getTeamNotes (teamPath: string, options = defaultOption) {
137+
if (options.unwrapData) {
138+
return this.axios.get<Note[]>(`teams/${teamPath}/notes`).then(response => response.data) as Promise<GetTeamNotes>
139+
} else {
140+
return this.axios.get<GetTeamNotes>(`teams/${teamPath}/notes`)
141+
}
101142
}
102143

103-
async createTeamNote (teamPath: string, options: CreateNoteOptions): Promise<CreateTeamNote> {
104-
const { data } = await this.axios.post<SingleNote>(`teams/${teamPath}/notes`, options)
105-
return data
144+
async createTeamNote (teamPath: string, payload: CreateNoteOptions, options = defaultOption) {
145+
if (options.unwrapData) {
146+
return this.axios.post<SingleNote>(`teams/${teamPath}/notes`, payload).then(response => response.data) as Promise<CreateTeamNote>
147+
} else {
148+
return this.axios.post<CreateTeamNote>(`teams/${teamPath}/notes`, payload)
149+
}
106150
}
107151

108-
async updateTeamNoteContent (teamPath: string, noteId: string, content?: string): Promise<UpdateTeamNote> {
109-
await this.axios.patch<AxiosResponse>(`teams/${teamPath}/notes/${noteId}`, { content })
152+
async updateTeamNoteContent (teamPath: string, noteId: string, content?: string): Promise<AxiosResponse> {
153+
return this.axios.patch<AxiosResponse>(`teams/${teamPath}/notes/${noteId}`, { content })
110154
}
111155

112156
async updateTeamNote (teamPath: string, noteId: string, options: Partial<Pick<SingleNote, 'content' | 'readPermission' | 'writePermission' | 'permalink'>>): Promise<AxiosResponse> {
113-
return await this.axios.patch<AxiosResponse>(`teams/${teamPath}/notes/${noteId}`, options)
157+
return this.axios.patch<AxiosResponse>(`teams/${teamPath}/notes/${noteId}`, options)
114158
}
115159

116-
async deleteTeamNote (teamPath: string, noteId: string): Promise<DeleteTeamNote> {
117-
await this.axios.delete<AxiosResponse>(`teams/${teamPath}/notes/${noteId}`)
160+
async deleteTeamNote (teamPath: string, noteId: string): Promise<AxiosResponse> {
161+
return this.axios.delete<AxiosResponse>(`teams/${teamPath}/notes/${noteId}`)
118162
}
119163
}
164+
165+
export default API

nodejs/tests/api.spec.ts

Lines changed: 20 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,30 @@
1-
import { startServer, stopServer } from './server'
1+
// import { startServer, stopServer } from './server'
2+
import { API } from '../src'
23

3-
let address: Awaited<ReturnType<typeof startServer>>
4+
// let address: Awaited<ReturnType<typeof startServer>>
5+
let client: API
46

57
beforeAll(async () => {
6-
address = await startServer()
8+
// address = await startServer()
79

8-
console.log(address)
10+
client = new API(process.env.HACKMD_ACCESS_TOKEN!, 'http://localhost:3000/api/openAPI/v1/')
11+
12+
// console.log(address)
913
})
1014

1115
afterAll(async () => {
12-
await stopServer()
16+
// await stopServer()
1317
})
1418

15-
test('it should respond with a 200 status code', async () => {
16-
expect(200).toBe(200)
19+
test('getMe', async () => {
20+
const response = await client.getMe({ unwrapData: false })
21+
22+
expect(response).toHaveProperty('status', 200)
23+
expect(response).toHaveProperty('headers')
24+
})
25+
26+
test('getMe unwrapped', async () => {
27+
const response = await client.getMe()
28+
29+
expect(typeof response).toBe('object')
1730
})

0 commit comments

Comments
 (0)