@model-match/api 3.43.1 → 3.44.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +121 -0
- package/RELEASE_NOTES.md +14 -0
- package/dist/{index-DUtNkw4G.d.mts → index-DMJ9eYSi.d.mts} +962 -2163
- package/dist/index.d.mts +2 -2
- package/dist/index.mjs +2 -2
- package/dist/slim/index.d.mts +481 -384
- package/dist/slim/index.mjs +4695 -5388
- package/dist/{src-B8pbncWy.mjs → src-DX-mM6Og.mjs} +844 -253
- package/openapi.json +779 -6926
- package/package.json +4 -25
|
@@ -1,188 +1,627 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
1
|
+
//#region src/core/bodySerializer.gen.ts
|
|
2
|
+
const jsonBodySerializer = { bodySerializer: (body) => JSON.stringify(body, (_key, value) => typeof value === "bigint" ? value.toString() : value) };
|
|
3
|
+
Object.entries({
|
|
4
|
+
$body_: "body",
|
|
5
|
+
$headers_: "headers",
|
|
6
|
+
$path_: "path",
|
|
7
|
+
$query_: "query"
|
|
7
8
|
});
|
|
8
9
|
//#endregion
|
|
9
|
-
//#region src/
|
|
10
|
-
|
|
10
|
+
//#region src/core/serverSentEvents.gen.ts
|
|
11
|
+
function createSseClient({ onRequest, onSseError, onSseEvent, responseTransformer, responseValidator, sseDefaultRetryDelay, sseMaxRetryAttempts, sseMaxRetryDelay, sseSleepFn, url, ...options }) {
|
|
12
|
+
let lastEventId;
|
|
13
|
+
const sleep = sseSleepFn ?? ((ms) => new Promise((resolve) => setTimeout(resolve, ms)));
|
|
14
|
+
const createStream = async function* () {
|
|
15
|
+
let retryDelay = sseDefaultRetryDelay ?? 3e3;
|
|
16
|
+
let attempt = 0;
|
|
17
|
+
const signal = options.signal ?? new AbortController().signal;
|
|
18
|
+
while (true) {
|
|
19
|
+
if (signal.aborted) break;
|
|
20
|
+
attempt++;
|
|
21
|
+
const headers = options.headers instanceof Headers ? options.headers : new Headers(options.headers);
|
|
22
|
+
if (lastEventId !== void 0) headers.set("Last-Event-ID", lastEventId);
|
|
23
|
+
try {
|
|
24
|
+
const requestInit = {
|
|
25
|
+
redirect: "follow",
|
|
26
|
+
...options,
|
|
27
|
+
body: options.serializedBody,
|
|
28
|
+
headers,
|
|
29
|
+
signal
|
|
30
|
+
};
|
|
31
|
+
let request = new Request(url, requestInit);
|
|
32
|
+
if (onRequest) request = await onRequest(url, requestInit);
|
|
33
|
+
const response = await (options.fetch ?? globalThis.fetch)(request);
|
|
34
|
+
if (!response.ok) throw new Error(`SSE failed: ${response.status} ${response.statusText}`);
|
|
35
|
+
if (!response.body) throw new Error("No body in SSE response");
|
|
36
|
+
const reader = response.body.pipeThrough(new TextDecoderStream()).getReader();
|
|
37
|
+
let buffer = "";
|
|
38
|
+
const abortHandler = () => {
|
|
39
|
+
try {
|
|
40
|
+
reader.cancel();
|
|
41
|
+
} catch {}
|
|
42
|
+
};
|
|
43
|
+
signal.addEventListener("abort", abortHandler);
|
|
44
|
+
try {
|
|
45
|
+
while (true) {
|
|
46
|
+
const { done, value } = await reader.read();
|
|
47
|
+
if (done) break;
|
|
48
|
+
buffer += value;
|
|
49
|
+
buffer = buffer.replace(/\r\n?/g, "\n");
|
|
50
|
+
const chunks = buffer.split("\n\n");
|
|
51
|
+
buffer = chunks.pop() ?? "";
|
|
52
|
+
for (const chunk of chunks) {
|
|
53
|
+
const lines = chunk.split("\n");
|
|
54
|
+
const dataLines = [];
|
|
55
|
+
let eventName;
|
|
56
|
+
for (const line of lines) if (line.startsWith("data:")) dataLines.push(line.replace(/^data:\s*/, ""));
|
|
57
|
+
else if (line.startsWith("event:")) eventName = line.replace(/^event:\s*/, "");
|
|
58
|
+
else if (line.startsWith("id:")) lastEventId = line.replace(/^id:\s*/, "");
|
|
59
|
+
else if (line.startsWith("retry:")) {
|
|
60
|
+
const parsed = Number.parseInt(line.replace(/^retry:\s*/, ""), 10);
|
|
61
|
+
if (!Number.isNaN(parsed)) retryDelay = parsed;
|
|
62
|
+
}
|
|
63
|
+
let data;
|
|
64
|
+
let parsedJson = false;
|
|
65
|
+
if (dataLines.length) {
|
|
66
|
+
const rawData = dataLines.join("\n");
|
|
67
|
+
try {
|
|
68
|
+
data = JSON.parse(rawData);
|
|
69
|
+
parsedJson = true;
|
|
70
|
+
} catch {
|
|
71
|
+
data = rawData;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
if (parsedJson) {
|
|
75
|
+
if (responseValidator) await responseValidator(data);
|
|
76
|
+
if (responseTransformer) data = await responseTransformer(data);
|
|
77
|
+
}
|
|
78
|
+
onSseEvent?.({
|
|
79
|
+
data,
|
|
80
|
+
event: eventName,
|
|
81
|
+
id: lastEventId,
|
|
82
|
+
retry: retryDelay
|
|
83
|
+
});
|
|
84
|
+
if (dataLines.length) yield data;
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
} finally {
|
|
88
|
+
signal.removeEventListener("abort", abortHandler);
|
|
89
|
+
reader.releaseLock();
|
|
90
|
+
}
|
|
91
|
+
break;
|
|
92
|
+
} catch (error) {
|
|
93
|
+
onSseError?.(error);
|
|
94
|
+
if (sseMaxRetryAttempts !== void 0 && attempt >= sseMaxRetryAttempts) break;
|
|
95
|
+
await sleep(Math.min(retryDelay * 2 ** (attempt - 1), sseMaxRetryDelay ?? 3e4));
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
};
|
|
99
|
+
return { stream: createStream() };
|
|
100
|
+
}
|
|
11
101
|
//#endregion
|
|
12
|
-
//#region src/
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
return (options.client ?? client).get({
|
|
20
|
-
security: [{
|
|
21
|
-
name: "x-api-key",
|
|
22
|
-
type: "apiKey"
|
|
23
|
-
}, {
|
|
24
|
-
scheme: "bearer",
|
|
25
|
-
type: "http"
|
|
26
|
-
}],
|
|
27
|
-
url: "/v1/admin/cad/links/{nmlsId}",
|
|
28
|
-
...options
|
|
29
|
-
});
|
|
102
|
+
//#region src/core/pathSerializer.gen.ts
|
|
103
|
+
const separatorArrayExplode = (style) => {
|
|
104
|
+
switch (style) {
|
|
105
|
+
case "label": return ".";
|
|
106
|
+
case "matrix": return ";";
|
|
107
|
+
case "simple": return ",";
|
|
108
|
+
default: return "&";
|
|
30
109
|
}
|
|
31
110
|
};
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
return (options?.client ?? client).get({
|
|
39
|
-
security: [{
|
|
40
|
-
name: "x-api-key",
|
|
41
|
-
type: "apiKey"
|
|
42
|
-
}, {
|
|
43
|
-
scheme: "bearer",
|
|
44
|
-
type: "http"
|
|
45
|
-
}],
|
|
46
|
-
url: "/v1/admin/contact-submissions",
|
|
47
|
-
...options
|
|
48
|
-
});
|
|
111
|
+
const separatorArrayNoExplode = (style) => {
|
|
112
|
+
switch (style) {
|
|
113
|
+
case "form": return ",";
|
|
114
|
+
case "pipeDelimited": return "|";
|
|
115
|
+
case "spaceDelimited": return "%20";
|
|
116
|
+
default: return ",";
|
|
49
117
|
}
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
type: "apiKey"
|
|
58
|
-
}, {
|
|
59
|
-
scheme: "bearer",
|
|
60
|
-
type: "http"
|
|
61
|
-
}],
|
|
62
|
-
url: "/v1/admin/contact-submissions/approved",
|
|
63
|
-
...options
|
|
64
|
-
});
|
|
65
|
-
}
|
|
66
|
-
/**
|
|
67
|
-
* Revoke an approved contact value (admin)
|
|
68
|
-
* Already revoked → 200 with the row unchanged.
|
|
69
|
-
*/
|
|
70
|
-
static adminRevokeApprovedContact(options) {
|
|
71
|
-
return (options.client ?? client).post({
|
|
72
|
-
security: [{
|
|
73
|
-
name: "x-api-key",
|
|
74
|
-
type: "apiKey"
|
|
75
|
-
}, {
|
|
76
|
-
scheme: "bearer",
|
|
77
|
-
type: "http"
|
|
78
|
-
}],
|
|
79
|
-
url: "/v1/admin/contact-submissions/approved/{id}/revoke",
|
|
80
|
-
...options,
|
|
81
|
-
headers: {
|
|
82
|
-
"Content-Type": "application/json",
|
|
83
|
-
...options?.headers
|
|
84
|
-
}
|
|
85
|
-
});
|
|
118
|
+
};
|
|
119
|
+
const separatorObjectExplode = (style) => {
|
|
120
|
+
switch (style) {
|
|
121
|
+
case "label": return ".";
|
|
122
|
+
case "matrix": return ";";
|
|
123
|
+
case "simple": return ",";
|
|
124
|
+
default: return "&";
|
|
86
125
|
}
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
126
|
+
};
|
|
127
|
+
const serializeArrayParam = ({ allowReserved, explode, name, style, value }) => {
|
|
128
|
+
if (!explode) {
|
|
129
|
+
const joinedValues = (allowReserved ? value : value.map((v) => encodeURIComponent(v))).join(separatorArrayNoExplode(style));
|
|
130
|
+
switch (style) {
|
|
131
|
+
case "label": return `.${joinedValues}`;
|
|
132
|
+
case "matrix": return `;${name}=${joinedValues}`;
|
|
133
|
+
case "simple": return joinedValues;
|
|
134
|
+
default: return `${name}=${joinedValues}`;
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
const separator = separatorArrayExplode(style);
|
|
138
|
+
const joinedValues = value.map((v) => {
|
|
139
|
+
if (style === "label" || style === "simple") return allowReserved ? v : encodeURIComponent(v);
|
|
140
|
+
return serializePrimitiveParam({
|
|
141
|
+
allowReserved,
|
|
142
|
+
name,
|
|
143
|
+
value: v
|
|
144
|
+
});
|
|
145
|
+
}).join(separator);
|
|
146
|
+
return style === "label" || style === "matrix" ? separator + joinedValues : joinedValues;
|
|
147
|
+
};
|
|
148
|
+
const serializePrimitiveParam = ({ allowReserved, name, value }) => {
|
|
149
|
+
if (value === void 0 || value === null) return "";
|
|
150
|
+
if (typeof value === "object") throw new Error("Deeply-nested arrays/objects aren’t supported. Provide your own `querySerializer()` to handle these.");
|
|
151
|
+
return `${name}=${allowReserved ? value : encodeURIComponent(value)}`;
|
|
152
|
+
};
|
|
153
|
+
const serializeObjectParam = ({ allowReserved, explode, name, style, value, valueOnly }) => {
|
|
154
|
+
if (value instanceof Date) return valueOnly ? value.toISOString() : `${name}=${value.toISOString()}`;
|
|
155
|
+
if (style !== "deepObject" && !explode) {
|
|
156
|
+
let values = [];
|
|
157
|
+
Object.entries(value).forEach(([key, v]) => {
|
|
158
|
+
values = [
|
|
159
|
+
...values,
|
|
160
|
+
key,
|
|
161
|
+
allowReserved ? v : encodeURIComponent(v)
|
|
162
|
+
];
|
|
163
|
+
});
|
|
164
|
+
const joinedValues = values.join(",");
|
|
165
|
+
switch (style) {
|
|
166
|
+
case "form": return `${name}=${joinedValues}`;
|
|
167
|
+
case "label": return `.${joinedValues}`;
|
|
168
|
+
case "matrix": return `;${name}=${joinedValues}`;
|
|
169
|
+
default: return joinedValues;
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
const separator = separatorObjectExplode(style);
|
|
173
|
+
const joinedValues = Object.entries(value).map(([key, v]) => serializePrimitiveParam({
|
|
174
|
+
allowReserved,
|
|
175
|
+
name: style === "deepObject" ? `${name}[${key}]` : key,
|
|
176
|
+
value: v
|
|
177
|
+
})).join(separator);
|
|
178
|
+
return style === "label" || style === "matrix" ? separator + joinedValues : joinedValues;
|
|
179
|
+
};
|
|
180
|
+
//#endregion
|
|
181
|
+
//#region src/core/utils.gen.ts
|
|
182
|
+
const PATH_PARAM_RE = /\{[^{}]+\}/g;
|
|
183
|
+
const defaultPathSerializer = ({ path, url: _url }) => {
|
|
184
|
+
let url = _url;
|
|
185
|
+
const matches = _url.match(PATH_PARAM_RE);
|
|
186
|
+
if (matches) for (const match of matches) {
|
|
187
|
+
let explode = false;
|
|
188
|
+
let name = match.substring(1, match.length - 1);
|
|
189
|
+
let style = "simple";
|
|
190
|
+
if (name.endsWith("*")) {
|
|
191
|
+
explode = true;
|
|
192
|
+
name = name.substring(0, name.length - 1);
|
|
193
|
+
}
|
|
194
|
+
if (name.startsWith(".")) {
|
|
195
|
+
name = name.substring(1);
|
|
196
|
+
style = "label";
|
|
197
|
+
} else if (name.startsWith(";")) {
|
|
198
|
+
name = name.substring(1);
|
|
199
|
+
style = "matrix";
|
|
200
|
+
}
|
|
201
|
+
const value = path[name];
|
|
202
|
+
if (value === void 0 || value === null) continue;
|
|
203
|
+
if (Array.isArray(value)) {
|
|
204
|
+
url = url.replace(match, serializeArrayParam({
|
|
205
|
+
explode,
|
|
206
|
+
name,
|
|
207
|
+
style,
|
|
208
|
+
value
|
|
209
|
+
}));
|
|
210
|
+
continue;
|
|
211
|
+
}
|
|
212
|
+
if (typeof value === "object") {
|
|
213
|
+
url = url.replace(match, serializeObjectParam({
|
|
214
|
+
explode,
|
|
215
|
+
name,
|
|
216
|
+
style,
|
|
217
|
+
value,
|
|
218
|
+
valueOnly: true
|
|
219
|
+
}));
|
|
220
|
+
continue;
|
|
221
|
+
}
|
|
222
|
+
if (style === "matrix") {
|
|
223
|
+
url = url.replace(match, `;${serializePrimitiveParam({
|
|
224
|
+
name,
|
|
225
|
+
value
|
|
226
|
+
})}`);
|
|
227
|
+
continue;
|
|
228
|
+
}
|
|
229
|
+
const replaceValue = encodeURIComponent(style === "label" ? `.${value}` : value);
|
|
230
|
+
url = url.replace(match, replaceValue);
|
|
231
|
+
}
|
|
232
|
+
return url;
|
|
233
|
+
};
|
|
234
|
+
const getUrl = ({ baseUrl, path, query, querySerializer, url: _url }) => {
|
|
235
|
+
const pathUrl = _url.startsWith("/") ? _url : `/${_url}`;
|
|
236
|
+
let url = (baseUrl ?? "") + pathUrl;
|
|
237
|
+
if (path) url = defaultPathSerializer({
|
|
238
|
+
path,
|
|
239
|
+
url
|
|
240
|
+
});
|
|
241
|
+
let search = query ? querySerializer(query) : "";
|
|
242
|
+
if (search.startsWith("?")) search = search.substring(1);
|
|
243
|
+
if (search) url += `?${search}`;
|
|
244
|
+
return url;
|
|
245
|
+
};
|
|
246
|
+
function getValidRequestBody(options) {
|
|
247
|
+
const hasBody = options.body !== void 0;
|
|
248
|
+
if (hasBody && options.bodySerializer) {
|
|
249
|
+
if ("serializedBody" in options) return options.serializedBody !== void 0 && options.serializedBody !== "" ? options.serializedBody : null;
|
|
250
|
+
return options.body !== "" ? options.body : null;
|
|
102
251
|
}
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
252
|
+
if (hasBody) return options.body;
|
|
253
|
+
}
|
|
254
|
+
//#endregion
|
|
255
|
+
//#region src/core/auth.gen.ts
|
|
256
|
+
const getAuthToken = async (auth, callback) => {
|
|
257
|
+
const token = typeof callback === "function" ? await callback(auth) : callback;
|
|
258
|
+
if (!token) return;
|
|
259
|
+
if (auth.scheme === "bearer") return `Bearer ${token}`;
|
|
260
|
+
if (auth.scheme === "basic") return `Basic ${btoa(token)}`;
|
|
261
|
+
return token;
|
|
262
|
+
};
|
|
263
|
+
//#endregion
|
|
264
|
+
//#region src/client/utils.gen.ts
|
|
265
|
+
const createQuerySerializer = ({ parameters = {}, ...args } = {}) => {
|
|
266
|
+
const querySerializer = (queryParams) => {
|
|
267
|
+
const search = [];
|
|
268
|
+
if (queryParams && typeof queryParams === "object") for (const name in queryParams) {
|
|
269
|
+
const value = queryParams[name];
|
|
270
|
+
if (value === void 0 || value === null) continue;
|
|
271
|
+
const options = parameters[name] || args;
|
|
272
|
+
if (Array.isArray(value)) {
|
|
273
|
+
const serializedArray = serializeArrayParam({
|
|
274
|
+
allowReserved: options.allowReserved,
|
|
275
|
+
explode: true,
|
|
276
|
+
name,
|
|
277
|
+
style: "form",
|
|
278
|
+
value,
|
|
279
|
+
...options.array
|
|
280
|
+
});
|
|
281
|
+
if (serializedArray) search.push(serializedArray);
|
|
282
|
+
} else if (typeof value === "object") {
|
|
283
|
+
const serializedObject = serializeObjectParam({
|
|
284
|
+
allowReserved: options.allowReserved,
|
|
285
|
+
explode: true,
|
|
286
|
+
name,
|
|
287
|
+
style: "deepObject",
|
|
288
|
+
value,
|
|
289
|
+
...options.object
|
|
290
|
+
});
|
|
291
|
+
if (serializedObject) search.push(serializedObject);
|
|
292
|
+
} else {
|
|
293
|
+
const serializedPrimitive = serializePrimitiveParam({
|
|
294
|
+
allowReserved: options.allowReserved,
|
|
295
|
+
name,
|
|
296
|
+
value
|
|
297
|
+
});
|
|
298
|
+
if (serializedPrimitive) search.push(serializedPrimitive);
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
return search.join("&");
|
|
302
|
+
};
|
|
303
|
+
return querySerializer;
|
|
304
|
+
};
|
|
305
|
+
/**
|
|
306
|
+
* Infers parseAs value from provided Content-Type header.
|
|
307
|
+
*/
|
|
308
|
+
const getParseAs = (contentType) => {
|
|
309
|
+
if (!contentType) return "stream";
|
|
310
|
+
const cleanContent = contentType.split(";")[0]?.trim();
|
|
311
|
+
if (!cleanContent) return;
|
|
312
|
+
if (cleanContent.startsWith("application/json") || cleanContent.endsWith("+json")) return "json";
|
|
313
|
+
if (cleanContent === "multipart/form-data") return "formData";
|
|
314
|
+
if ([
|
|
315
|
+
"application/",
|
|
316
|
+
"audio/",
|
|
317
|
+
"image/",
|
|
318
|
+
"video/"
|
|
319
|
+
].some((type) => cleanContent.startsWith(type))) return "blob";
|
|
320
|
+
if (cleanContent.startsWith("text/")) return "text";
|
|
321
|
+
};
|
|
322
|
+
const checkForExistence = (options, name) => {
|
|
323
|
+
if (!name) return false;
|
|
324
|
+
if (options.headers.has(name) || options.query?.[name] || options.headers.get("Cookie")?.includes(`${name}=`)) return true;
|
|
325
|
+
return false;
|
|
326
|
+
};
|
|
327
|
+
async function setAuthParams(options) {
|
|
328
|
+
for (const auth of options.security ?? []) {
|
|
329
|
+
if (checkForExistence(options, auth.name)) continue;
|
|
330
|
+
const token = await getAuthToken(auth, options.auth);
|
|
331
|
+
if (!token) continue;
|
|
332
|
+
const name = auth.name ?? "Authorization";
|
|
333
|
+
switch (auth.in) {
|
|
334
|
+
case "query":
|
|
335
|
+
if (!options.query) options.query = {};
|
|
336
|
+
options.query[name] = token;
|
|
337
|
+
break;
|
|
338
|
+
case "cookie":
|
|
339
|
+
options.headers.append("Cookie", `${name}=${token}`);
|
|
340
|
+
break;
|
|
341
|
+
default:
|
|
342
|
+
options.headers.set(name, token);
|
|
343
|
+
break;
|
|
344
|
+
}
|
|
123
345
|
}
|
|
346
|
+
}
|
|
347
|
+
const buildUrl = (options) => getUrl({
|
|
348
|
+
baseUrl: options.baseUrl,
|
|
349
|
+
path: options.path,
|
|
350
|
+
query: options.query,
|
|
351
|
+
querySerializer: typeof options.querySerializer === "function" ? options.querySerializer : createQuerySerializer(options.querySerializer),
|
|
352
|
+
url: options.url
|
|
353
|
+
});
|
|
354
|
+
const mergeConfigs = (a, b) => {
|
|
355
|
+
const config = {
|
|
356
|
+
...a,
|
|
357
|
+
...b
|
|
358
|
+
};
|
|
359
|
+
if (config.baseUrl?.endsWith("/")) config.baseUrl = config.baseUrl.substring(0, config.baseUrl.length - 1);
|
|
360
|
+
config.headers = mergeHeaders(a.headers, b.headers);
|
|
361
|
+
return config;
|
|
124
362
|
};
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
363
|
+
const headersEntries = (headers) => {
|
|
364
|
+
const entries = [];
|
|
365
|
+
headers.forEach((value, key) => {
|
|
366
|
+
entries.push([key, value]);
|
|
367
|
+
});
|
|
368
|
+
return entries;
|
|
369
|
+
};
|
|
370
|
+
const mergeHeaders = (...headers) => {
|
|
371
|
+
const mergedHeaders = new Headers();
|
|
372
|
+
for (const header of headers) {
|
|
373
|
+
if (!header) continue;
|
|
374
|
+
const iterator = header instanceof Headers ? headersEntries(header) : Object.entries(header);
|
|
375
|
+
for (const [key, value] of iterator) if (value === null) mergedHeaders.delete(key);
|
|
376
|
+
else if (Array.isArray(value)) for (const v of value) mergedHeaders.append(key, v);
|
|
377
|
+
else if (value !== void 0) mergedHeaders.set(key, typeof value === "object" ? JSON.stringify(value) : value);
|
|
378
|
+
}
|
|
379
|
+
return mergedHeaders;
|
|
380
|
+
};
|
|
381
|
+
var Interceptors = class {
|
|
382
|
+
fns = [];
|
|
383
|
+
clear() {
|
|
384
|
+
this.fns = [];
|
|
385
|
+
}
|
|
386
|
+
eject(id) {
|
|
387
|
+
const index = this.getInterceptorIndex(id);
|
|
388
|
+
if (this.fns[index]) this.fns[index] = null;
|
|
389
|
+
}
|
|
390
|
+
exists(id) {
|
|
391
|
+
const index = this.getInterceptorIndex(id);
|
|
392
|
+
return Boolean(this.fns[index]);
|
|
393
|
+
}
|
|
394
|
+
getInterceptorIndex(id) {
|
|
395
|
+
if (typeof id === "number") return this.fns[id] ? id : -1;
|
|
396
|
+
return this.fns.indexOf(id);
|
|
397
|
+
}
|
|
398
|
+
update(id, fn) {
|
|
399
|
+
const index = this.getInterceptorIndex(id);
|
|
400
|
+
if (this.fns[index]) {
|
|
401
|
+
this.fns[index] = fn;
|
|
402
|
+
return id;
|
|
403
|
+
}
|
|
404
|
+
return false;
|
|
405
|
+
}
|
|
406
|
+
use(fn) {
|
|
407
|
+
this.fns.push(fn);
|
|
408
|
+
return this.fns.length - 1;
|
|
142
409
|
}
|
|
143
410
|
};
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
...options
|
|
159
|
-
});
|
|
411
|
+
const createInterceptors = () => ({
|
|
412
|
+
error: new Interceptors(),
|
|
413
|
+
request: new Interceptors(),
|
|
414
|
+
response: new Interceptors()
|
|
415
|
+
});
|
|
416
|
+
const defaultQuerySerializer = createQuerySerializer({
|
|
417
|
+
allowReserved: false,
|
|
418
|
+
array: {
|
|
419
|
+
explode: true,
|
|
420
|
+
style: "form"
|
|
421
|
+
},
|
|
422
|
+
object: {
|
|
423
|
+
explode: true,
|
|
424
|
+
style: "deepObject"
|
|
160
425
|
}
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
426
|
+
});
|
|
427
|
+
const defaultHeaders = { "Content-Type": "application/json" };
|
|
428
|
+
const createConfig = (override = {}) => ({
|
|
429
|
+
...jsonBodySerializer,
|
|
430
|
+
headers: defaultHeaders,
|
|
431
|
+
parseAs: "auto",
|
|
432
|
+
querySerializer: defaultQuerySerializer,
|
|
433
|
+
...override
|
|
434
|
+
});
|
|
435
|
+
//#endregion
|
|
436
|
+
//#region src/client/client.gen.ts
|
|
437
|
+
const createClient$1 = (config = {}) => {
|
|
438
|
+
let _config = mergeConfigs(createConfig(), config);
|
|
439
|
+
const getConfig = () => ({ ..._config });
|
|
440
|
+
const setConfig = (config) => {
|
|
441
|
+
_config = mergeConfigs(_config, config);
|
|
442
|
+
return getConfig();
|
|
443
|
+
};
|
|
444
|
+
const interceptors = createInterceptors();
|
|
445
|
+
const beforeRequest = async (options) => {
|
|
446
|
+
const opts = {
|
|
447
|
+
..._config,
|
|
448
|
+
...options,
|
|
449
|
+
fetch: options.fetch ?? _config.fetch ?? globalThis.fetch,
|
|
450
|
+
headers: mergeHeaders(_config.headers, options.headers),
|
|
451
|
+
serializedBody: void 0
|
|
452
|
+
};
|
|
453
|
+
if (opts.security) await setAuthParams(opts);
|
|
454
|
+
if (opts.requestValidator) await opts.requestValidator(opts);
|
|
455
|
+
if (opts.body !== void 0 && opts.bodySerializer) opts.serializedBody = opts.bodySerializer(opts.body);
|
|
456
|
+
if (opts.body === void 0 || opts.serializedBody === "") opts.headers.delete("Content-Type");
|
|
457
|
+
const resolvedOpts = opts;
|
|
458
|
+
return {
|
|
459
|
+
opts: resolvedOpts,
|
|
460
|
+
url: buildUrl(resolvedOpts)
|
|
461
|
+
};
|
|
462
|
+
};
|
|
463
|
+
const request = async (options) => {
|
|
464
|
+
const throwOnError = options.throwOnError ?? _config.throwOnError;
|
|
465
|
+
const responseStyle = options.responseStyle ?? _config.responseStyle;
|
|
466
|
+
let request;
|
|
467
|
+
let response;
|
|
468
|
+
try {
|
|
469
|
+
const { opts, url } = await beforeRequest(options);
|
|
470
|
+
const requestInit = {
|
|
471
|
+
redirect: "follow",
|
|
472
|
+
...opts,
|
|
473
|
+
body: getValidRequestBody(opts)
|
|
474
|
+
};
|
|
475
|
+
request = new Request(url, requestInit);
|
|
476
|
+
for (const fn of interceptors.request.fns) if (fn) request = await fn(request, opts);
|
|
477
|
+
const _fetch = opts.fetch;
|
|
478
|
+
response = await _fetch(request);
|
|
479
|
+
for (const fn of interceptors.response.fns) if (fn) response = await fn(response, request, opts);
|
|
480
|
+
const result = {
|
|
481
|
+
request,
|
|
482
|
+
response
|
|
483
|
+
};
|
|
484
|
+
if (response.ok) {
|
|
485
|
+
const parseAs = (opts.parseAs === "auto" ? getParseAs(response.headers.get("Content-Type")) : opts.parseAs) ?? "json";
|
|
486
|
+
if (response.status === 204 || response.headers.get("Content-Length") === "0") {
|
|
487
|
+
let emptyData;
|
|
488
|
+
switch (parseAs) {
|
|
489
|
+
case "arrayBuffer":
|
|
490
|
+
case "blob":
|
|
491
|
+
case "text":
|
|
492
|
+
emptyData = await response[parseAs]();
|
|
493
|
+
break;
|
|
494
|
+
case "formData":
|
|
495
|
+
emptyData = new FormData();
|
|
496
|
+
break;
|
|
497
|
+
case "stream":
|
|
498
|
+
emptyData = response.body;
|
|
499
|
+
break;
|
|
500
|
+
default:
|
|
501
|
+
emptyData = {};
|
|
502
|
+
break;
|
|
503
|
+
}
|
|
504
|
+
return opts.responseStyle === "data" ? emptyData : {
|
|
505
|
+
data: emptyData,
|
|
506
|
+
...result
|
|
507
|
+
};
|
|
508
|
+
}
|
|
509
|
+
let data;
|
|
510
|
+
switch (parseAs) {
|
|
511
|
+
case "arrayBuffer":
|
|
512
|
+
case "blob":
|
|
513
|
+
case "formData":
|
|
514
|
+
case "text":
|
|
515
|
+
data = await response[parseAs]();
|
|
516
|
+
break;
|
|
517
|
+
case "json": {
|
|
518
|
+
const text = await response.text();
|
|
519
|
+
data = text ? JSON.parse(text) : {};
|
|
520
|
+
break;
|
|
521
|
+
}
|
|
522
|
+
case "stream": return opts.responseStyle === "data" ? response.body : {
|
|
523
|
+
data: response.body,
|
|
524
|
+
...result
|
|
525
|
+
};
|
|
526
|
+
}
|
|
527
|
+
if (parseAs === "json") {
|
|
528
|
+
if (opts.responseValidator) await opts.responseValidator(data);
|
|
529
|
+
if (opts.responseTransformer) data = await opts.responseTransformer(data);
|
|
530
|
+
}
|
|
531
|
+
return opts.responseStyle === "data" ? data : {
|
|
532
|
+
data,
|
|
533
|
+
...result
|
|
534
|
+
};
|
|
535
|
+
}
|
|
536
|
+
const textError = await response.text();
|
|
537
|
+
let jsonError;
|
|
538
|
+
try {
|
|
539
|
+
jsonError = JSON.parse(textError);
|
|
540
|
+
} catch {}
|
|
541
|
+
throw jsonError ?? textError;
|
|
542
|
+
} catch (error) {
|
|
543
|
+
let finalError = error;
|
|
544
|
+
for (const fn of interceptors.error.fns) if (fn) finalError = await fn(finalError, response, request, options);
|
|
545
|
+
finalError = finalError || {};
|
|
546
|
+
if (throwOnError) throw finalError;
|
|
547
|
+
return responseStyle === "data" ? void 0 : {
|
|
548
|
+
error: finalError,
|
|
549
|
+
request,
|
|
550
|
+
response
|
|
551
|
+
};
|
|
552
|
+
}
|
|
553
|
+
};
|
|
554
|
+
const makeMethodFn = (method) => (options) => request({
|
|
555
|
+
...options,
|
|
556
|
+
method
|
|
557
|
+
});
|
|
558
|
+
const makeSseFn = (method) => async (options) => {
|
|
559
|
+
const { opts, url } = await beforeRequest(options);
|
|
560
|
+
return createSseClient({
|
|
561
|
+
...opts,
|
|
562
|
+
body: opts.body,
|
|
563
|
+
method,
|
|
564
|
+
onRequest: async (url, init) => {
|
|
565
|
+
let request = new Request(url, init);
|
|
566
|
+
for (const fn of interceptors.request.fns) if (fn) request = await fn(request, opts);
|
|
567
|
+
return request;
|
|
568
|
+
},
|
|
569
|
+
serializedBody: getValidRequestBody(opts),
|
|
570
|
+
url
|
|
180
571
|
});
|
|
181
|
-
}
|
|
572
|
+
};
|
|
573
|
+
const _buildUrl = (options) => buildUrl({
|
|
574
|
+
..._config,
|
|
575
|
+
...options
|
|
576
|
+
});
|
|
577
|
+
return {
|
|
578
|
+
buildUrl: _buildUrl,
|
|
579
|
+
connect: makeMethodFn("CONNECT"),
|
|
580
|
+
delete: makeMethodFn("DELETE"),
|
|
581
|
+
get: makeMethodFn("GET"),
|
|
582
|
+
getConfig,
|
|
583
|
+
head: makeMethodFn("HEAD"),
|
|
584
|
+
interceptors,
|
|
585
|
+
options: makeMethodFn("OPTIONS"),
|
|
586
|
+
patch: makeMethodFn("PATCH"),
|
|
587
|
+
post: makeMethodFn("POST"),
|
|
588
|
+
put: makeMethodFn("PUT"),
|
|
589
|
+
request,
|
|
590
|
+
setConfig,
|
|
591
|
+
sse: {
|
|
592
|
+
connect: makeSseFn("CONNECT"),
|
|
593
|
+
delete: makeSseFn("DELETE"),
|
|
594
|
+
get: makeSseFn("GET"),
|
|
595
|
+
head: makeSseFn("HEAD"),
|
|
596
|
+
options: makeSseFn("OPTIONS"),
|
|
597
|
+
patch: makeSseFn("PATCH"),
|
|
598
|
+
post: makeSseFn("POST"),
|
|
599
|
+
put: makeSseFn("PUT"),
|
|
600
|
+
trace: makeSseFn("TRACE")
|
|
601
|
+
},
|
|
602
|
+
trace: makeMethodFn("TRACE")
|
|
603
|
+
};
|
|
182
604
|
};
|
|
605
|
+
//#endregion
|
|
606
|
+
//#region src/runtime-config.ts
|
|
607
|
+
/** `MMR_API_URL` when set (non-prod / local), else production. */
|
|
608
|
+
function defaultBaseUrl() {
|
|
609
|
+
return (typeof process === "undefined" ? void 0 : process.env?.MMR_API_URL) ?? "https://api.modelmatch.com";
|
|
610
|
+
}
|
|
611
|
+
const createClientConfig = (config) => ({
|
|
612
|
+
...config,
|
|
613
|
+
throwOnError: true,
|
|
614
|
+
baseUrl: config?.baseUrl ?? defaultBaseUrl()
|
|
615
|
+
});
|
|
616
|
+
//#endregion
|
|
617
|
+
//#region src/client.gen.ts
|
|
618
|
+
const client = createClient$1(createClientConfig(createConfig()));
|
|
619
|
+
//#endregion
|
|
620
|
+
//#region src/sdk.gen.ts
|
|
183
621
|
var Agents = class {
|
|
184
622
|
/**
|
|
185
623
|
* Search agents with filters
|
|
624
|
+
*
|
|
186
625
|
* Search and list individual real-estate agents with filters — one row per agent. Filter by name, location (state, city, zip), brokerage/office, and production metrics (sales volume, transaction units, price range), with sorting and cursor pagination. LOCATION SEMANTICS: the state/city/zip filters match ANY of an agent's location signals — their listed city/state, their office address(es), AND the markets where they actually closed transactions (production) — combined with OR. So an agent matches a searched location if their office OR their production is there (set `locationSource` to `office` or `production` to use one signal). A search for city "Long Beach" can therefore return agents whose office or displayed primary market is in a different city/state, because they transacted in Long Beach. The `state`/`city` returned on each row reflect the agent's primary market and may differ from the searched location. (Use the `office` filter to match by brokerage/office name — one or several names, each a case-insensitive whole-word phrase, `name*` for a prefix; `currentOffice` restricts to the agent's current office — and the per-agent city/county/state breakdown endpoints to rank an agent's volume within a specific market.) RANKING BY DEAL SIDE: combine a location filter with `sort` on `buyerVolume`/`buyerUnits` (or `sellerVolume`/`sellerUnits`, `dualVolume`/`dualUnits`) to rank agents by how active they are representing buyers vs. sellers in that market — e.g. sort `buyerVolume` descending for the most active buyer-side agents in a state or city. This is the per-agent record search: use it to find specific real-estate agents or build a filtered agent list. (For a single agent by ID use the agent detail endpoint.) If you only need how many agents match and not the records themselves, send the same request body to `countAgents`.
|
|
187
626
|
*/
|
|
188
627
|
static list(options) {
|
|
@@ -264,6 +703,7 @@ var Agents = class {
|
|
|
264
703
|
}
|
|
265
704
|
/**
|
|
266
705
|
* Submit a bulk-delivery job for agents
|
|
706
|
+
*
|
|
267
707
|
* Queues an ECS task that dumps every matching agents document to S3 in the requested format. Returns 202 with a jobId; poll `GET /v1/agents/bulk-delivery/{jobId}` for status + the signed download URL.
|
|
268
708
|
*
|
|
269
709
|
* **Row limit.** Deliveries of up to 5,000 rows need no entitlement. Above that, the org's `bulk-delivery.agents` entitlement is required and its scope (row ceiling, row filters, allowed fields) governs the delivery; without it the request is rejected with 403 `entitlement_missing`. Pass `limit` at or below the ceiling to deliver a capped subset of a broader query. Email support@modelmatch.com to request a limit increase.
|
|
@@ -291,6 +731,7 @@ var Agents = class {
|
|
|
291
731
|
}
|
|
292
732
|
/**
|
|
293
733
|
* Cancel a bulk-delivery job for agents
|
|
734
|
+
*
|
|
294
735
|
* Cancels a queued or running agents delivery job.
|
|
295
736
|
*
|
|
296
737
|
* The job is marked `cancelled` immediately; the container running it notices on its next page boundary and stops. Because a delivery is billed once, at the end, **a cancelled job is never charged** — no credits are debited and there is nothing to refund. No partial file is written.
|
|
@@ -328,6 +769,7 @@ var Agents = class {
|
|
|
328
769
|
}
|
|
329
770
|
/**
|
|
330
771
|
* Submit contact details for a real estate agent
|
|
772
|
+
*
|
|
331
773
|
* Send contact details you know for a real estate agent — a phone number, an email address, a profile link, or the company they moved to. The submission is checked and reviewed before anything appears on the profile; this call only records it and answers immediately. Sending the same details for the same person again while the first submission is still being reviewed returns the first submission's `id`.
|
|
332
774
|
*/
|
|
333
775
|
static createAgentContactSubmission(options) {
|
|
@@ -349,6 +791,7 @@ var Agents = class {
|
|
|
349
791
|
}
|
|
350
792
|
/**
|
|
351
793
|
* Count agents matching filters
|
|
794
|
+
*
|
|
352
795
|
* Return the exact number of agents matching the given filters. Accepts the same request body as `listAgents` (pagination and sort are ignored). Use this when you only need a total; to get the matching agents themselves, send the same request body to `listAgents`.
|
|
353
796
|
*/
|
|
354
797
|
static count(options) {
|
|
@@ -386,6 +829,7 @@ var Agents = class {
|
|
|
386
829
|
}
|
|
387
830
|
/**
|
|
388
831
|
* Financing profile of the agent's deals, per side
|
|
832
|
+
*
|
|
389
833
|
* Scoped to the agent's FINANCED deals: recorded loans on which the agent is the buyer's agent or the listing / co-listing agent, matched through the agent's MLS ids. Cash deals carry no loan and are not counted. The date window is the loan's recording date. Returns, for each side at once (`any`, `buyer`, `listing` — duals on `buyer`): the financed deal count and loan volume, how many were brokered (third-party origination), and the loan-type mix. For the prior period, call again with that period.
|
|
390
834
|
*/
|
|
391
835
|
static loanMix(options) {
|
|
@@ -401,12 +845,13 @@ var Agents = class {
|
|
|
401
845
|
...options,
|
|
402
846
|
headers: {
|
|
403
847
|
"Content-Type": "application/json",
|
|
404
|
-
...options
|
|
848
|
+
...options.headers
|
|
405
849
|
}
|
|
406
850
|
});
|
|
407
851
|
}
|
|
408
852
|
/**
|
|
409
853
|
* The agent's financed deals and loan volume, over time
|
|
854
|
+
*
|
|
410
855
|
* Scoped to the agent's FINANCED deals: recorded loans on which the agent is the buyer's agent or the listing / co-listing agent, matched through the agent's MLS ids. Cash deals carry no loan and are not counted. The date window is the loan's recording date. One bucket per `interval` (default monthly): `units` = financed deals recorded in the bucket, `volume` = their total loan amount (out-of-range fill amounts excluded and counted in `excluded`). `previous` is the same series for the prior window. `side` defaults to `any`; `buyer` + `listing` = `any` per bucket. Pair with `agentAnalyticsTimeSeries` (closed sales by sale date) for a mortgaged-vs-total chart — the two use different date axes (loan recording vs sale close), so a deal can land a month apart.
|
|
411
856
|
*/
|
|
412
857
|
static mortgagedTimeSeries(options) {
|
|
@@ -422,12 +867,13 @@ var Agents = class {
|
|
|
422
867
|
...options,
|
|
423
868
|
headers: {
|
|
424
869
|
"Content-Type": "application/json",
|
|
425
|
-
...options
|
|
870
|
+
...options.headers
|
|
426
871
|
}
|
|
427
872
|
});
|
|
428
873
|
}
|
|
429
874
|
/**
|
|
430
875
|
* Home builders on the agent's deals (pre-aggregated)
|
|
876
|
+
*
|
|
431
877
|
* New-construction builders named on the agent's deals in the period, ranked by units. Spellings of one builder are one row (case, punctuation, legal suffixes such as LLC, a trailing "of <State>", generic words such as Homes, letter typos) with `units` summed; `label` / `id` are those of its most common spelling, and distinct companies (a builder's subsidiaries) stay separate. Feed placeholders ("Unknown", "Unk", "N/A", "-", "TBD", "None", "Other", …) are not builders and are dropped. The pre-aggregated builder list carries a deal COUNT only, so every row's `volume` and `pctVolume` are 0 — rank and share by `units` / `pctUnits` (a share of ALL the agent's deals in the period, so the rows sum to the builder-sold share, not to 1). It carries no buyer/listing split either: `side` must be `any` (or omitted); `buyer`/`listing` return 400.
|
|
432
878
|
*/
|
|
433
879
|
static builders(options) {
|
|
@@ -443,12 +889,13 @@ var Agents = class {
|
|
|
443
889
|
...options,
|
|
444
890
|
headers: {
|
|
445
891
|
"Content-Type": "application/json",
|
|
446
|
-
...options
|
|
892
|
+
...options.headers
|
|
447
893
|
}
|
|
448
894
|
});
|
|
449
895
|
}
|
|
450
896
|
/**
|
|
451
897
|
* City volume breakdown across the agent's sales
|
|
898
|
+
*
|
|
452
899
|
* Ranks the agent's CLOSED sales (MLS status sold, a real sale price — rentals and lease listings excluded, duplicate MLS records of one sale counted once) by this dimension. The same population `POST /v1/agents/{id}/sales` returns with `flatFilters.mlsStatus: "SLD"` and the agent analytics routes count. `side` narrows to the deals the agent was on that side of (`buyer` includes deals on both sides; `buyer` + `listing` = `any`).
|
|
453
900
|
*/
|
|
454
901
|
static cities(options) {
|
|
@@ -464,7 +911,7 @@ var Agents = class {
|
|
|
464
911
|
...options,
|
|
465
912
|
headers: {
|
|
466
913
|
"Content-Type": "application/json",
|
|
467
|
-
...options
|
|
914
|
+
...options.headers
|
|
468
915
|
}
|
|
469
916
|
});
|
|
470
917
|
}
|
|
@@ -484,12 +931,13 @@ var Agents = class {
|
|
|
484
931
|
...options,
|
|
485
932
|
headers: {
|
|
486
933
|
"Content-Type": "application/json",
|
|
487
|
-
...options
|
|
934
|
+
...options.headers
|
|
488
935
|
}
|
|
489
936
|
});
|
|
490
937
|
}
|
|
491
938
|
/**
|
|
492
939
|
* County (FIPS) volume breakdown
|
|
940
|
+
*
|
|
493
941
|
* Ranks the agent's CLOSED sales (MLS status sold, a real sale price — rentals and lease listings excluded, duplicate MLS records of one sale counted once) by this dimension. The same population `POST /v1/agents/{id}/sales` returns with `flatFilters.mlsStatus: "SLD"` and the agent analytics routes count. `side` narrows to the deals the agent was on that side of (`buyer` includes deals on both sides; `buyer` + `listing` = `any`).
|
|
494
942
|
*/
|
|
495
943
|
static counties(options) {
|
|
@@ -505,12 +953,13 @@ var Agents = class {
|
|
|
505
953
|
...options,
|
|
506
954
|
headers: {
|
|
507
955
|
"Content-Type": "application/json",
|
|
508
|
-
...options
|
|
956
|
+
...options.headers
|
|
509
957
|
}
|
|
510
958
|
});
|
|
511
959
|
}
|
|
512
960
|
/**
|
|
513
961
|
* Lenders on the agent's deals (pre-aggregated)
|
|
962
|
+
*
|
|
514
963
|
* Lenders that financed the agent's deals in the period. Each row's `id` is the lender id — pass it back as the `lender` filter on the loans routes to drill into that lender's loans — and `label` its display name. The row for deals with no lender attributed carries no `id`.
|
|
515
964
|
*/
|
|
516
965
|
static lenders(options) {
|
|
@@ -526,12 +975,13 @@ var Agents = class {
|
|
|
526
975
|
...options,
|
|
527
976
|
headers: {
|
|
528
977
|
"Content-Type": "application/json",
|
|
529
|
-
...options
|
|
978
|
+
...options.headers
|
|
530
979
|
}
|
|
531
980
|
});
|
|
532
981
|
}
|
|
533
982
|
/**
|
|
534
983
|
* Offices the agent closed deals through (their side of each sale)
|
|
984
|
+
*
|
|
535
985
|
* Ranks the agent's CLOSED sales (MLS status sold, a real sale price — rentals and lease listings excluded, duplicate MLS records of one sale counted once) by this dimension. The same population `POST /v1/agents/{id}/sales` returns with `flatFilters.mlsStatus: "SLD"` and the agent analytics routes count. `side` narrows to the deals the agent was on that side of (`buyer` includes deals on both sides; `buyer` + `listing` = `any`). Each sale is credited to the office recorded for the agent's OWN side of it (the listing office when the agent listed it, including dual deals; the buyer's office when the agent only represented the buyer), so every sale counts at most once. A sale with no office recorded on the agent's side lands in no row, so rows can sum to less than `totals`. Office names are as recorded and not normalized: one brokerage can appear under several spellings.
|
|
536
986
|
*/
|
|
537
987
|
static offices(options) {
|
|
@@ -547,7 +997,7 @@ var Agents = class {
|
|
|
547
997
|
...options,
|
|
548
998
|
headers: {
|
|
549
999
|
"Content-Type": "application/json",
|
|
550
|
-
...options
|
|
1000
|
+
...options.headers
|
|
551
1001
|
}
|
|
552
1002
|
});
|
|
553
1003
|
}
|
|
@@ -567,12 +1017,13 @@ var Agents = class {
|
|
|
567
1017
|
...options,
|
|
568
1018
|
headers: {
|
|
569
1019
|
"Content-Type": "application/json",
|
|
570
|
-
...options
|
|
1020
|
+
...options.headers
|
|
571
1021
|
}
|
|
572
1022
|
});
|
|
573
1023
|
}
|
|
574
1024
|
/**
|
|
575
1025
|
* State volume breakdown
|
|
1026
|
+
*
|
|
576
1027
|
* Ranks the agent's CLOSED sales (MLS status sold, a real sale price — rentals and lease listings excluded, duplicate MLS records of one sale counted once) by this dimension. The same population `POST /v1/agents/{id}/sales` returns with `flatFilters.mlsStatus: "SLD"` and the agent analytics routes count. `side` narrows to the deals the agent was on that side of (`buyer` includes deals on both sides; `buyer` + `listing` = `any`).
|
|
577
1028
|
*/
|
|
578
1029
|
static states(options) {
|
|
@@ -588,12 +1039,13 @@ var Agents = class {
|
|
|
588
1039
|
...options,
|
|
589
1040
|
headers: {
|
|
590
1041
|
"Content-Type": "application/json",
|
|
591
|
-
...options
|
|
1042
|
+
...options.headers
|
|
592
1043
|
}
|
|
593
1044
|
});
|
|
594
1045
|
}
|
|
595
1046
|
/**
|
|
596
1047
|
* Title companies on the agent's financed deals (spellings merged)
|
|
1048
|
+
*
|
|
597
1049
|
* Scoped to the agent's FINANCED deals: recorded loans on which the agent is the buyer's agent or the listing / co-listing agent, matched through the agent's MLS ids. Cash deals carry no loan and are not counted. The date window is the loan's recording date. Ranks the title companies named on those loans. Spellings of one company are MERGED: `label` is its most-used spelling, `id` the normalized name every spelling was grouped under. "None available"-style placeholders and names shorter than 3 characters are excluded. `pctUnits` / `pctVolume` are shares of ALL the side's financed deals in the window, including those with no title company, so they do not sum to 1. `side` defaults to `any`; title company is usually picked on the buyer side, so `buyer` is the view that reads as "who this agent's buyers close with".
|
|
598
1050
|
*/
|
|
599
1051
|
static titleCompanies(options) {
|
|
@@ -609,12 +1061,13 @@ var Agents = class {
|
|
|
609
1061
|
...options,
|
|
610
1062
|
headers: {
|
|
611
1063
|
"Content-Type": "application/json",
|
|
612
|
-
...options
|
|
1064
|
+
...options.headers
|
|
613
1065
|
}
|
|
614
1066
|
});
|
|
615
1067
|
}
|
|
616
1068
|
/**
|
|
617
1069
|
* Title companies on the agent's financed deals, over time
|
|
1070
|
+
*
|
|
618
1071
|
* Scoped to the agent's FINANCED deals: recorded loans on which the agent is the buyer's agent or the listing / co-listing agent, matched through the agent's MLS ids. Cash deals carry no loan and are not counted. The date window is the loan's recording date. One bucket per `interval` (default monthly), each segmented by title company with spellings merged per bucket: `segments[].label` is the company's most-used spelling across the whole response and `segments[].id` the normalized name — match a company across buckets on `id`. `previous` is the same series for the prior window. `side` defaults to `any`.
|
|
619
1072
|
*/
|
|
620
1073
|
static titleCompaniesTimeSeries(options) {
|
|
@@ -630,12 +1083,13 @@ var Agents = class {
|
|
|
630
1083
|
...options,
|
|
631
1084
|
headers: {
|
|
632
1085
|
"Content-Type": "application/json",
|
|
633
|
-
...options
|
|
1086
|
+
...options.headers
|
|
634
1087
|
}
|
|
635
1088
|
});
|
|
636
1089
|
}
|
|
637
1090
|
/**
|
|
638
1091
|
* Zip-code volume breakdown
|
|
1092
|
+
*
|
|
639
1093
|
* Ranks the agent's CLOSED sales (MLS status sold, a real sale price — rentals and lease listings excluded, duplicate MLS records of one sale counted once) by this dimension. The same population `POST /v1/agents/{id}/sales` returns with `flatFilters.mlsStatus: "SLD"` and the agent analytics routes count. `side` narrows to the deals the agent was on that side of (`buyer` includes deals on both sides; `buyer` + `listing` = `any`).
|
|
640
1094
|
*/
|
|
641
1095
|
static zipCodes(options) {
|
|
@@ -651,12 +1105,13 @@ var Agents = class {
|
|
|
651
1105
|
...options,
|
|
652
1106
|
headers: {
|
|
653
1107
|
"Content-Type": "application/json",
|
|
654
|
-
...options
|
|
1108
|
+
...options.headers
|
|
655
1109
|
}
|
|
656
1110
|
});
|
|
657
1111
|
}
|
|
658
1112
|
/**
|
|
659
1113
|
* The ZIP markets this agent works, blended
|
|
1114
|
+
*
|
|
660
1115
|
* Rank the ZIP markets one real-estate agent works, with volume, transaction counts and mean sale price per market, plus a weighted summary across the whole footprint. Optionally narrow to a ZIP list or a date window. REACH, NOT MARKET SHARE: an agent belongs to every market they touch — where their office is AND everywhere they have transacted — so one agent is counted in several markets at once. Per-market agent counts therefore over-sum: they cannot be added together, and dividing one into a total does not produce a market share. The only percentage returned, `shareOfScope`, is each market's share of this agent's volume across the scope requested and sums to 100 over that scope; there is no share-of-whole-book figure, because the transaction records carry no per-agent total to divide by. TWO COUNTS, ON PURPOSE: `transactions` counts transaction records; `units` counts the ones carrying a price, which are the records behind `volume` and `avgSalePrice`. Roughly half of an agent's records are priced, so dividing volume by `transactions` understates the average by about 2×. Figures are computed live from the agent's transaction records — an agent record carries no stored market rollup — and are ranked across their busiest ZIP markets. When a ZIP scope returns no markets, `reach.presentInScope` distinguishes 'works there, nothing closed in the window' from 'not present at all'. The summary also carries a Community Lending mix: what kind of neighborhood these markets are, weighted by the agent's activity in each. These are U.S. Census tract-level aggregates describing whole neighborhoods — never an individual, household or client attribute — and on this surface the basis is always the markets in scope, since an agent record carries no stored neighborhood rollup.
|
|
661
1116
|
*/
|
|
662
1117
|
static markets(options) {
|
|
@@ -672,7 +1127,7 @@ var Agents = class {
|
|
|
672
1127
|
...options,
|
|
673
1128
|
headers: {
|
|
674
1129
|
"Content-Type": "application/json",
|
|
675
|
-
...options
|
|
1130
|
+
...options.headers
|
|
676
1131
|
}
|
|
677
1132
|
});
|
|
678
1133
|
}
|
|
@@ -692,12 +1147,13 @@ var Agents = class {
|
|
|
692
1147
|
...options,
|
|
693
1148
|
headers: {
|
|
694
1149
|
"Content-Type": "application/json",
|
|
695
|
-
...options
|
|
1150
|
+
...options.headers
|
|
696
1151
|
}
|
|
697
1152
|
});
|
|
698
1153
|
}
|
|
699
1154
|
/**
|
|
700
1155
|
* Sales transactions where this agent was listing or selling side
|
|
1156
|
+
*
|
|
701
1157
|
* The agent's deals, newest first: every sale on which the agent is the buyer's agent or the listing / co-listing agent. `side` narrows to one half (`buyer` includes deals where the agent was on both sides; `listing` excludes them). Each row says which `side` the agent was on and carries the sale's recorded purchase `loan` — lender, loan officer, loan type, amount, title company — or `null` for a cash deal or a loan not yet on file. Pass `flatFilters.mlsStatus: "SLD"` for closed deals only. `dealFilters` adds an address `search`, the co-listing agent, builder / status-date filters and loan-side filters (`financed`, `loan.*` on the purchase loan). Sorts: the `/v1/sales` names plus `listDate`, `builder`, `coListAgent`, and the loan / party columns `loanAmount`, `loanType`, `loanTransactionType`, `interestRate`, `lenderName`, `originatorName`, `companyName`, `brokerName`, `titleCompany`, `buyerName`, `sellerName`, `downPayment` (one at a time; blanks last). `listingAgent` / `soldAgent` / `coListAgent` order by the name the row shows.
|
|
702
1158
|
*/
|
|
703
1159
|
static sales(options) {
|
|
@@ -713,7 +1169,7 @@ var Agents = class {
|
|
|
713
1169
|
...options,
|
|
714
1170
|
headers: {
|
|
715
1171
|
"Content-Type": "application/json",
|
|
716
|
-
...options
|
|
1172
|
+
...options.headers
|
|
717
1173
|
}
|
|
718
1174
|
});
|
|
719
1175
|
}
|
|
@@ -721,6 +1177,7 @@ var Agents = class {
|
|
|
721
1177
|
var Related = class {
|
|
722
1178
|
/**
|
|
723
1179
|
* Records linked to this one
|
|
1180
|
+
*
|
|
724
1181
|
* Return the ids of records of another type that are linked to this record. Links resolve by identifier, strongest identifier first, and equally-trusted identifiers are combined — a company's linked loans cover every role it holds on a loan, not just the first one found. The response reports which strength was used: `primary` is the canonical identifier for that pair, `secondary` is a real but weaker alternate used only when the record carries nothing better. This is a lightweight index: it returns ids and a count, not full records. For filtering, sorting, pagination and full detail, use the named endpoint for the pair (for example the originator loans endpoint) and fetch records by id.
|
|
725
1182
|
*/
|
|
726
1183
|
static agent(options) {
|
|
@@ -738,6 +1195,7 @@ var Related = class {
|
|
|
738
1195
|
}
|
|
739
1196
|
/**
|
|
740
1197
|
* Records linked to this one
|
|
1198
|
+
*
|
|
741
1199
|
* Return the ids of records of another type that are linked to this record. Links resolve by identifier, strongest identifier first, and equally-trusted identifiers are combined — a company's linked loans cover every role it holds on a loan, not just the first one found. The response reports which strength was used: `primary` is the canonical identifier for that pair, `secondary` is a real but weaker alternate used only when the record carries nothing better. This is a lightweight index: it returns ids and a count, not full records. For filtering, sorting, pagination and full detail, use the named endpoint for the pair (for example the originator loans endpoint) and fetch records by id.
|
|
742
1200
|
*/
|
|
743
1201
|
static company(options) {
|
|
@@ -755,6 +1213,7 @@ var Related = class {
|
|
|
755
1213
|
}
|
|
756
1214
|
/**
|
|
757
1215
|
* Records linked to this one
|
|
1216
|
+
*
|
|
758
1217
|
* Return the ids of records of another type that are linked to this record. Links resolve by identifier, strongest identifier first, and equally-trusted identifiers are combined — a company's linked loans cover every role it holds on a loan, not just the first one found. The response reports which strength was used: `primary` is the canonical identifier for that pair, `secondary` is a real but weaker alternate used only when the record carries nothing better. This is a lightweight index: it returns ids and a count, not full records. For filtering, sorting, pagination and full detail, use the named endpoint for the pair (for example the originator loans endpoint) and fetch records by id.
|
|
759
1218
|
*/
|
|
760
1219
|
static loan(options) {
|
|
@@ -772,6 +1231,7 @@ var Related = class {
|
|
|
772
1231
|
}
|
|
773
1232
|
/**
|
|
774
1233
|
* Records linked to this one
|
|
1234
|
+
*
|
|
775
1235
|
* Return the ids of records of another type that are linked to this record. Links resolve by identifier, strongest identifier first, and equally-trusted identifiers are combined — a company's linked loans cover every role it holds on a loan, not just the first one found. The response reports which strength was used: `primary` is the canonical identifier for that pair, `secondary` is a real but weaker alternate used only when the record carries nothing better. This is a lightweight index: it returns ids and a count, not full records. For filtering, sorting, pagination and full detail, use the named endpoint for the pair (for example the originator loans endpoint) and fetch records by id.
|
|
776
1236
|
*/
|
|
777
1237
|
static originator(options) {
|
|
@@ -789,6 +1249,7 @@ var Related = class {
|
|
|
789
1249
|
}
|
|
790
1250
|
/**
|
|
791
1251
|
* Records linked to this one
|
|
1252
|
+
*
|
|
792
1253
|
* Return the ids of records of another type that are linked to this record. Links resolve by identifier, strongest identifier first, and equally-trusted identifiers are combined — a company's linked loans cover every role it holds on a loan, not just the first one found. The response reports which strength was used: `primary` is the canonical identifier for that pair, `secondary` is a real but weaker alternate used only when the record carries nothing better. This is a lightweight index: it returns ids and a count, not full records. For filtering, sorting, pagination and full detail, use the named endpoint for the pair (for example the originator loans endpoint) and fetch records by id.
|
|
793
1254
|
*/
|
|
794
1255
|
static property(options) {
|
|
@@ -806,6 +1267,7 @@ var Related = class {
|
|
|
806
1267
|
}
|
|
807
1268
|
/**
|
|
808
1269
|
* Records linked to this one
|
|
1270
|
+
*
|
|
809
1271
|
* Return the ids of records of another type that are linked to this record. Links resolve by identifier, strongest identifier first, and equally-trusted identifiers are combined — a company's linked loans cover every role it holds on a loan, not just the first one found. The response reports which strength was used: `primary` is the canonical identifier for that pair, `secondary` is a real but weaker alternate used only when the record carries nothing better. This is a lightweight index: it returns ids and a count, not full records. For filtering, sorting, pagination and full detail, use the named endpoint for the pair (for example the originator loans endpoint) and fetch records by id.
|
|
810
1272
|
*/
|
|
811
1273
|
static sale(options) {
|
|
@@ -841,6 +1303,7 @@ var Alerts = class {
|
|
|
841
1303
|
}
|
|
842
1304
|
/**
|
|
843
1305
|
* Update your alert settings
|
|
1306
|
+
*
|
|
844
1307
|
* Saves your NMLS id, contact identity and tunables. The per-trigger `enabled` flags are deprecated: subscribe to alert recipes or manage subscriptions instead. While still accepted, `enabled[type]: true` turns the trigger on for every watched subject that supports it, and `false` turns it off everywhere.
|
|
845
1308
|
*/
|
|
846
1309
|
static updateAlertConditions(options) {
|
|
@@ -894,6 +1357,7 @@ var Alerts = class {
|
|
|
894
1357
|
}
|
|
895
1358
|
/**
|
|
896
1359
|
* Preview an alert email template
|
|
1360
|
+
*
|
|
897
1361
|
* Validates an email template and returns the notification props a run would send with it, filled with sample items for the given kinds — your recent alerts of those kinds when you have any, else samples. Writes nothing. Pass `recipeId` to preview under one of your recipes (or a published one).
|
|
898
1362
|
*/
|
|
899
1363
|
static previewAlertEmailTemplate(options) {
|
|
@@ -915,6 +1379,7 @@ var Alerts = class {
|
|
|
915
1379
|
}
|
|
916
1380
|
/**
|
|
917
1381
|
* List the alert email template tokens
|
|
1382
|
+
*
|
|
918
1383
|
* The tokens a recipe email template can use: run-level tokens (anywhere) and the item tokens each alert kind offers (inside an `items` block), each with a label and a formatted example.
|
|
919
1384
|
*/
|
|
920
1385
|
static getAlertEmailTokens(options) {
|
|
@@ -980,6 +1445,7 @@ var Alerts = class {
|
|
|
980
1445
|
}
|
|
981
1446
|
/**
|
|
982
1447
|
* List your own alert recipes
|
|
1448
|
+
*
|
|
983
1449
|
* The alert recipes you created (any status), with whether you are subscribed to each. Active ones also appear on GET /alerts/recipes with `scope: "mine"`.
|
|
984
1450
|
*/
|
|
985
1451
|
static listMyAlertRecipes(options) {
|
|
@@ -997,6 +1463,7 @@ var Alerts = class {
|
|
|
997
1463
|
}
|
|
998
1464
|
/**
|
|
999
1465
|
* Create your own alert recipe
|
|
1466
|
+
*
|
|
1000
1467
|
* Creates an alert recipe only you can see and subscribe to (at most 10). Give a title, the alert kinds per subject type (`grants`), and optionally a description, icon and inputs; the notification family, default inputs and digest copy are derived. Subscribe to it with POST /alerts/recipes/{id}.
|
|
1001
1468
|
*/
|
|
1002
1469
|
static createMyAlertRecipe(options) {
|
|
@@ -1018,6 +1485,7 @@ var Alerts = class {
|
|
|
1018
1485
|
}
|
|
1019
1486
|
/**
|
|
1020
1487
|
* Preview an unsaved alert recipe
|
|
1488
|
+
*
|
|
1021
1489
|
* Dry-runs a recipe definition (not saved) over the last 30 days for you, with the given inputs applied on top of your saved setup. Writes nothing.
|
|
1022
1490
|
*/
|
|
1023
1491
|
static previewMyAlertRecipe(options) {
|
|
@@ -1039,6 +1507,7 @@ var Alerts = class {
|
|
|
1039
1507
|
}
|
|
1040
1508
|
/**
|
|
1041
1509
|
* Delete your own alert recipe
|
|
1510
|
+
*
|
|
1042
1511
|
* Deletes the recipe and unsubscribes you from it. Saved agents, areas and records stay.
|
|
1043
1512
|
*/
|
|
1044
1513
|
static deleteMyAlertRecipe(options) {
|
|
@@ -1056,6 +1525,7 @@ var Alerts = class {
|
|
|
1056
1525
|
}
|
|
1057
1526
|
/**
|
|
1058
1527
|
* Update your own alert recipe
|
|
1528
|
+
*
|
|
1059
1529
|
* Replaces the definition (`version` bumps). Your existing subscription to it narrows to the kinds it still grants.
|
|
1060
1530
|
*/
|
|
1061
1531
|
static updateMyAlertRecipe(options) {
|
|
@@ -1071,12 +1541,13 @@ var Alerts = class {
|
|
|
1071
1541
|
...options,
|
|
1072
1542
|
headers: {
|
|
1073
1543
|
"Content-Type": "application/json",
|
|
1074
|
-
...options
|
|
1544
|
+
...options.headers
|
|
1075
1545
|
}
|
|
1076
1546
|
});
|
|
1077
1547
|
}
|
|
1078
1548
|
/**
|
|
1079
1549
|
* Preview the alerts that would fire for you
|
|
1550
|
+
*
|
|
1080
1551
|
* Runs all six detectors scoped to your own token, in-process and synchronously, as a dry-run: returns the alerts that WOULD fire (per detector, with the decision payloads) without writing the feed, publishing events, or sending email.
|
|
1081
1552
|
*/
|
|
1082
1553
|
static preview(options) {
|
|
@@ -1098,6 +1569,7 @@ var Alerts = class {
|
|
|
1098
1569
|
}
|
|
1099
1570
|
/**
|
|
1100
1571
|
* List alert recipes
|
|
1572
|
+
*
|
|
1101
1573
|
* The published alert recipes — named bundles of alert triggers — with the inputs each needs and whether you are subscribed, followed by your own recipes (`scope: "mine"`).
|
|
1102
1574
|
*/
|
|
1103
1575
|
static listAlertRecipes(options) {
|
|
@@ -1115,6 +1587,7 @@ var Alerts = class {
|
|
|
1115
1587
|
}
|
|
1116
1588
|
/**
|
|
1117
1589
|
* Unsubscribe from an alert recipe
|
|
1590
|
+
*
|
|
1118
1591
|
* Turns the recipe's alert triggers off. Saved agents, areas and records stay; remove them with the watch-list endpoints.
|
|
1119
1592
|
*/
|
|
1120
1593
|
static unsubscribeAlertRecipe(options) {
|
|
@@ -1132,6 +1605,7 @@ var Alerts = class {
|
|
|
1132
1605
|
}
|
|
1133
1606
|
/**
|
|
1134
1607
|
* Subscribe to an alert recipe
|
|
1608
|
+
*
|
|
1135
1609
|
* Turns on the recipe's alert triggers, saves its inputs (NMLS id, agents, areas or a record — see the recipe's `inputs`), and backfills recent matches. For a record input, empty rules apply the recipe's rule templates for the record type.
|
|
1136
1610
|
*/
|
|
1137
1611
|
static subscribeAlertRecipe(options) {
|
|
@@ -1147,12 +1621,13 @@ var Alerts = class {
|
|
|
1147
1621
|
...options,
|
|
1148
1622
|
headers: {
|
|
1149
1623
|
"Content-Type": "application/json",
|
|
1150
|
-
...options
|
|
1624
|
+
...options.headers
|
|
1151
1625
|
}
|
|
1152
1626
|
});
|
|
1153
1627
|
}
|
|
1154
1628
|
/**
|
|
1155
1629
|
* Preview an alert recipe
|
|
1630
|
+
*
|
|
1156
1631
|
* Dry-run the recipe over the last 30 days for you, with the given inputs applied on top of your saved ones. Writes nothing.
|
|
1157
1632
|
*/
|
|
1158
1633
|
static previewAlertRecipe(options) {
|
|
@@ -1168,12 +1643,13 @@ var Alerts = class {
|
|
|
1168
1643
|
...options,
|
|
1169
1644
|
headers: {
|
|
1170
1645
|
"Content-Type": "application/json",
|
|
1171
|
-
...options
|
|
1646
|
+
...options.headers
|
|
1172
1647
|
}
|
|
1173
1648
|
});
|
|
1174
1649
|
}
|
|
1175
1650
|
/**
|
|
1176
1651
|
* List your alert subscriptions
|
|
1652
|
+
*
|
|
1177
1653
|
* Every subject you watch — agents, areas, your NMLS id, records — with the alert kinds that fire on it and the recipes that turned them on.
|
|
1178
1654
|
*/
|
|
1179
1655
|
static listAlertSubscriptions(options) {
|
|
@@ -1191,6 +1667,7 @@ var Alerts = class {
|
|
|
1191
1667
|
}
|
|
1192
1668
|
/**
|
|
1193
1669
|
* Subscribe to alerts on a subject
|
|
1670
|
+
*
|
|
1194
1671
|
* Watch a subject (an agent, an area, your NMLS id, or a sale / property / loan with rules) for the given alert kinds. Re-posting the same subject replaces the kinds you set directly; kinds a recipe turned on stay. Recent matches are backfilled when kinds are added.
|
|
1195
1672
|
*/
|
|
1196
1673
|
static createAlertSubscription(options) {
|
|
@@ -1212,6 +1689,7 @@ var Alerts = class {
|
|
|
1212
1689
|
}
|
|
1213
1690
|
/**
|
|
1214
1691
|
* Remove an alert subscription
|
|
1692
|
+
*
|
|
1215
1693
|
* Stops watching the subject (idempotent). For a record watch this also forgets its baseline, so watching it again starts fresh.
|
|
1216
1694
|
*/
|
|
1217
1695
|
static deleteAlertSubscription(options) {
|
|
@@ -1403,6 +1881,7 @@ var Alerts = class {
|
|
|
1403
1881
|
var Branches = class {
|
|
1404
1882
|
/**
|
|
1405
1883
|
* Search branches with filters
|
|
1884
|
+
*
|
|
1406
1885
|
* Search NMLS-registered mortgage company branch offices (not MLS real estate offices — use listOffices for those). Returns branch name, address, parent company, managers, and NMLS ID. Each row carries branch-level production metrics for the selected period. If you only need how many branches match and not the records themselves, send the same request body to `countBranches`.
|
|
1407
1886
|
*/
|
|
1408
1887
|
static list(options) {
|
|
@@ -1424,6 +1903,7 @@ var Branches = class {
|
|
|
1424
1903
|
}
|
|
1425
1904
|
/**
|
|
1426
1905
|
* Configurable chart (measure × slice) over a branch roster's loans
|
|
1906
|
+
*
|
|
1427
1907
|
* Scoped to loans written by the loan officers on this branch's CURRENT licensing roster (wherever they wrote them), matching the branch profile. For loans public record attributes to the branch itself, use the branch breakdown endpoints.
|
|
1428
1908
|
*/
|
|
1429
1909
|
static analyticsChart(options) {
|
|
@@ -1445,6 +1925,7 @@ var Branches = class {
|
|
|
1445
1925
|
}
|
|
1446
1926
|
/**
|
|
1447
1927
|
* Branch roster production summary with previous-period comparison
|
|
1928
|
+
*
|
|
1448
1929
|
* Scoped to loans written by the loan officers on this branch's CURRENT licensing roster (wherever they wrote them), matching the branch profile. For loans public record attributes to the branch itself, use the branch breakdown endpoints.
|
|
1449
1930
|
*/
|
|
1450
1931
|
static analyticsSummary(options) {
|
|
@@ -1466,6 +1947,7 @@ var Branches = class {
|
|
|
1466
1947
|
}
|
|
1467
1948
|
/**
|
|
1468
1949
|
* Branch roster volume / units over time
|
|
1950
|
+
*
|
|
1469
1951
|
* Scoped to loans written by the loan officers on this branch's CURRENT licensing roster (wherever they wrote them), matching the branch profile. For loans public record attributes to the branch itself, use the branch breakdown endpoints.
|
|
1470
1952
|
*/
|
|
1471
1953
|
static analyticsTimeSeries(options) {
|
|
@@ -1487,6 +1969,7 @@ var Branches = class {
|
|
|
1487
1969
|
}
|
|
1488
1970
|
/**
|
|
1489
1971
|
* Submit a bulk-delivery job for branches
|
|
1972
|
+
*
|
|
1490
1973
|
* Queues an ECS task that dumps every matching branches document to S3 in the requested format. Returns 202 with a jobId; poll `GET /v1/branches/bulk-delivery/{jobId}` for status + the signed download URL.
|
|
1491
1974
|
*
|
|
1492
1975
|
* **Row limit.** Deliveries of up to 5,000 rows need no entitlement. Above that, the org's `bulk-delivery.branches` entitlement is required and its scope (row ceiling, row filters, allowed fields) governs the delivery; without it the request is rejected with 403 `entitlement_missing`. Pass `limit` at or below the ceiling to deliver a capped subset of a broader query. Email support@modelmatch.com to request a limit increase.
|
|
@@ -1514,6 +1997,7 @@ var Branches = class {
|
|
|
1514
1997
|
}
|
|
1515
1998
|
/**
|
|
1516
1999
|
* Cancel a bulk-delivery job for branches
|
|
2000
|
+
*
|
|
1517
2001
|
* Cancels a queued or running branches delivery job.
|
|
1518
2002
|
*
|
|
1519
2003
|
* The job is marked `cancelled` immediately; the container running it notices on its next page boundary and stops. Because a delivery is billed once, at the end, **a cancelled job is never charged** — no credits are debited and there is nothing to refund. No partial file is written.
|
|
@@ -1551,6 +2035,7 @@ var Branches = class {
|
|
|
1551
2035
|
}
|
|
1552
2036
|
/**
|
|
1553
2037
|
* Count branches matching filters
|
|
2038
|
+
*
|
|
1554
2039
|
* Return the exact number of branches matching the given filters. Accepts the same request body as `listBranches` (pagination and sort are ignored). Use this when you only need a total; to get the matching branches themselves, send the same request body to `listBranches`.
|
|
1555
2040
|
*/
|
|
1556
2041
|
static count(options) {
|
|
@@ -1572,6 +2057,7 @@ var Branches = class {
|
|
|
1572
2057
|
}
|
|
1573
2058
|
/**
|
|
1574
2059
|
* Get branch by NMLS ID
|
|
2060
|
+
*
|
|
1575
2061
|
* Retrieve full details for a single NMLS mortgage branch including name, address, parent company, managers, trade names, licensing, and branch-level production for the selected period.
|
|
1576
2062
|
*/
|
|
1577
2063
|
static get(options) {
|
|
@@ -1589,6 +2075,7 @@ var Branches = class {
|
|
|
1589
2075
|
}
|
|
1590
2076
|
/**
|
|
1591
2077
|
* City volume breakdown across this branch's loans
|
|
2078
|
+
*
|
|
1592
2079
|
* Ranks the cities this branch's loans were secured in, by volume — the branch's real lending footprint rather than its parent company's. Labels are Title Case so they match the city breakdowns on every other entity.
|
|
1593
2080
|
*/
|
|
1594
2081
|
static cities(options) {
|
|
@@ -1604,12 +2091,13 @@ var Branches = class {
|
|
|
1604
2091
|
...options,
|
|
1605
2092
|
headers: {
|
|
1606
2093
|
"Content-Type": "application/json",
|
|
1607
|
-
...options
|
|
2094
|
+
...options.headers
|
|
1608
2095
|
}
|
|
1609
2096
|
});
|
|
1610
2097
|
}
|
|
1611
2098
|
/**
|
|
1612
2099
|
* County volume breakdown across this branch's loans
|
|
2100
|
+
*
|
|
1613
2101
|
* Ranks the counties this branch's loans were secured in, by volume. Labels are county codes on this surface — the same axis every other county breakdown uses, so the two are directly comparable.
|
|
1614
2102
|
*/
|
|
1615
2103
|
static counties(options) {
|
|
@@ -1625,12 +2113,13 @@ var Branches = class {
|
|
|
1625
2113
|
...options,
|
|
1626
2114
|
headers: {
|
|
1627
2115
|
"Content-Type": "application/json",
|
|
1628
|
-
...options
|
|
2116
|
+
...options.headers
|
|
1629
2117
|
}
|
|
1630
2118
|
});
|
|
1631
2119
|
}
|
|
1632
2120
|
/**
|
|
1633
2121
|
* Lenders this branch originated through
|
|
2122
|
+
*
|
|
1634
2123
|
* Ranks the lenders this branch's loans funded through, by volume. Pass an item's `id` — not its `label` — back as a `lender` filter value; `label` is the display name.
|
|
1635
2124
|
*/
|
|
1636
2125
|
static lenders(options) {
|
|
@@ -1646,12 +2135,13 @@ var Branches = class {
|
|
|
1646
2135
|
...options,
|
|
1647
2136
|
headers: {
|
|
1648
2137
|
"Content-Type": "application/json",
|
|
1649
|
-
...options
|
|
2138
|
+
...options.headers
|
|
1650
2139
|
}
|
|
1651
2140
|
});
|
|
1652
2141
|
}
|
|
1653
2142
|
/**
|
|
1654
2143
|
* Loan officers who wrote this branch's loans
|
|
2144
|
+
*
|
|
1655
2145
|
* Ranks the loan officers whose loans public record attributes to this branch, by volume. Each label is the LO's NMLS ID, so it chains straight into `GET /v1/originators/{nmlsId}`. This is the branch's RECORDED roster, not its licensing roster: it answers who actually wrote loans here in the period, which is narrower than everyone registered to the branch and can include someone who has since moved. For the licensed managers on file, read `managers` on `GET /v1/branches/{nmlsId}`.
|
|
1656
2146
|
*/
|
|
1657
2147
|
static originators(options) {
|
|
@@ -1667,12 +2157,13 @@ var Branches = class {
|
|
|
1667
2157
|
...options,
|
|
1668
2158
|
headers: {
|
|
1669
2159
|
"Content-Type": "application/json",
|
|
1670
|
-
...options
|
|
2160
|
+
...options.headers
|
|
1671
2161
|
}
|
|
1672
2162
|
});
|
|
1673
2163
|
}
|
|
1674
2164
|
/**
|
|
1675
2165
|
* State volume breakdown across this branch's loans
|
|
2166
|
+
*
|
|
1676
2167
|
* Ranks the states this branch's loans were secured in, by volume. Labels are two-letter state abbreviations. This is where the branch actually transacted, which is narrower than where it is licensed — licensed states are returned by `GET /v1/branches/{nmlsId}`.
|
|
1677
2168
|
*/
|
|
1678
2169
|
static states(options) {
|
|
@@ -1688,12 +2179,13 @@ var Branches = class {
|
|
|
1688
2179
|
...options,
|
|
1689
2180
|
headers: {
|
|
1690
2181
|
"Content-Type": "application/json",
|
|
1691
|
-
...options
|
|
2182
|
+
...options.headers
|
|
1692
2183
|
}
|
|
1693
2184
|
});
|
|
1694
2185
|
}
|
|
1695
2186
|
/**
|
|
1696
2187
|
* Title companies on this branch's loans (spellings merged)
|
|
2188
|
+
*
|
|
1697
2189
|
* Ranks the title companies on this entity's loans (recorded deeds, `recording_date` window — the same population and period axis as every other loans breakdown). Spellings of one company are MERGED: `label` is its most-used spelling, `id` the normalized name every spelling was grouped under (legal-form and filler words such as `inc`, `llc`, `co`, `company`, `title`, `escrow` removed; `natl` → `national`). Placeholder entries meaning "no title company recorded" (`none available` and its misspellings, `unknown`, `n/a`, …) and names shorter than 3 characters are excluded rather than ranked. `attorney` and `accommodation` are kept: they say who closed. `pctUnits` / `pctVolume` are shares of the entity's WHOLE loan population in the window, including loans with no title company, so they do not sum to 100 across the page. Pages of up to 100 via `pagination`.
|
|
1698
2190
|
*/
|
|
1699
2191
|
static titleCompanies(options) {
|
|
@@ -1709,12 +2201,13 @@ var Branches = class {
|
|
|
1709
2201
|
...options,
|
|
1710
2202
|
headers: {
|
|
1711
2203
|
"Content-Type": "application/json",
|
|
1712
|
-
...options
|
|
2204
|
+
...options.headers
|
|
1713
2205
|
}
|
|
1714
2206
|
});
|
|
1715
2207
|
}
|
|
1716
2208
|
/**
|
|
1717
2209
|
* Loans written by this branch
|
|
2210
|
+
*
|
|
1718
2211
|
* Returns the individual loans attributed to this branch office — the branch's own book, not its parent company's. Accepts the same filters, sorts and pagination as the main loan search. Attribution comes from public record, so this is the branch's recorded footprint and can be smaller than the production totals on `GET /v1/branches/{nmlsId}`.
|
|
1719
2212
|
*/
|
|
1720
2213
|
static loans(options) {
|
|
@@ -1730,12 +2223,13 @@ var Branches = class {
|
|
|
1730
2223
|
...options,
|
|
1731
2224
|
headers: {
|
|
1732
2225
|
"Content-Type": "application/json",
|
|
1733
|
-
...options
|
|
2226
|
+
...options.headers
|
|
1734
2227
|
}
|
|
1735
2228
|
});
|
|
1736
2229
|
}
|
|
1737
2230
|
/**
|
|
1738
2231
|
* Loan officers on this branch's current roster
|
|
2232
|
+
*
|
|
1739
2233
|
* The loan officers currently registered to this branch location who hold an active sponsorship or registration — one row per person, with current employer, tenure, years in the industry, manager flags and collected contact info. This is the LICENSING roster; for the loan officers whose loans public record attributes to the branch, use `branchOriginators`.
|
|
1740
2234
|
*/
|
|
1741
2235
|
static roster(options) {
|
|
@@ -1751,7 +2245,7 @@ var Branches = class {
|
|
|
1751
2245
|
...options,
|
|
1752
2246
|
headers: {
|
|
1753
2247
|
"Content-Type": "application/json",
|
|
1754
|
-
...options
|
|
2248
|
+
...options.headers
|
|
1755
2249
|
}
|
|
1756
2250
|
});
|
|
1757
2251
|
}
|
|
@@ -1759,6 +2253,7 @@ var Branches = class {
|
|
|
1759
2253
|
var Companies = class {
|
|
1760
2254
|
/**
|
|
1761
2255
|
* Search companies with filters
|
|
2256
|
+
*
|
|
1762
2257
|
* Search and list individual mortgage companies with filters — one row per company. Filter by name, NMLS ID, location (state, county, city, zip), and production metrics (loan volume, units, market share) by period and geography, with sorting and cursor pagination. This is the per-company record search: use it to find specific mortgage lenders/companies or build a filtered company list. (For a single company by ID use the company detail endpoint.) If you only need how many companies match and not the records themselves, send the same request body to `countCompanies`.
|
|
1763
2258
|
*/
|
|
1764
2259
|
static list(options) {
|
|
@@ -1840,6 +2335,7 @@ var Companies = class {
|
|
|
1840
2335
|
}
|
|
1841
2336
|
/**
|
|
1842
2337
|
* Submit a bulk-delivery job for companies
|
|
2338
|
+
*
|
|
1843
2339
|
* Queues an ECS task that dumps every matching companies document to S3 in the requested format. Returns 202 with a jobId; poll `GET /v1/companies/bulk-delivery/{jobId}` for status + the signed download URL.
|
|
1844
2340
|
*
|
|
1845
2341
|
* **Row limit.** Deliveries of up to 5,000 rows need no entitlement. Above that, the org's `bulk-delivery.companies` entitlement is required and its scope (row ceiling, row filters, allowed fields) governs the delivery; without it the request is rejected with 403 `entitlement_missing`. Pass `limit` at or below the ceiling to deliver a capped subset of a broader query. Email support@modelmatch.com to request a limit increase.
|
|
@@ -1867,6 +2363,7 @@ var Companies = class {
|
|
|
1867
2363
|
}
|
|
1868
2364
|
/**
|
|
1869
2365
|
* Cancel a bulk-delivery job for companies
|
|
2366
|
+
*
|
|
1870
2367
|
* Cancels a queued or running companies delivery job.
|
|
1871
2368
|
*
|
|
1872
2369
|
* The job is marked `cancelled` immediately; the container running it notices on its next page boundary and stops. Because a delivery is billed once, at the end, **a cancelled job is never charged** — no credits are debited and there is nothing to refund. No partial file is written.
|
|
@@ -1904,6 +2401,7 @@ var Companies = class {
|
|
|
1904
2401
|
}
|
|
1905
2402
|
/**
|
|
1906
2403
|
* Count companies matching filters
|
|
2404
|
+
*
|
|
1907
2405
|
* Return the exact number of companies matching the given filters. Accepts the same request body as `listCompanies` (pagination and sort are ignored). Use this when you only need a total; to get the matching companies themselves, send the same request body to `listCompanies`.
|
|
1908
2406
|
*/
|
|
1909
2407
|
static count(options) {
|
|
@@ -1925,6 +2423,7 @@ var Companies = class {
|
|
|
1925
2423
|
}
|
|
1926
2424
|
/**
|
|
1927
2425
|
* Look up companies in the NMLS registry
|
|
2426
|
+
*
|
|
1928
2427
|
* Search the NMLS company registry by id, name, registered address, regulator category and size — one row per registered company, INCLUDING companies with no production on file (which `listCompanies` does not return). Use it to resolve canonical company names for a list of NMLS ids, or to filter/sort companies by `regulatorCategory`, `branchCount`, `activeLoCount` or `avgTenureMonths`. For production metrics use `listCompanies`.
|
|
1929
2428
|
*/
|
|
1930
2429
|
static lookup(options) {
|
|
@@ -1976,12 +2475,13 @@ var Companies = class {
|
|
|
1976
2475
|
...options,
|
|
1977
2476
|
headers: {
|
|
1978
2477
|
"Content-Type": "application/json",
|
|
1979
|
-
...options
|
|
2478
|
+
...options.headers
|
|
1980
2479
|
}
|
|
1981
2480
|
});
|
|
1982
2481
|
}
|
|
1983
2482
|
/**
|
|
1984
2483
|
* Real-estate agents who co-closed with this company's LOs
|
|
2484
|
+
*
|
|
1985
2485
|
* Ranks the real-estate agents on the selling side of this company's loans, by volume. Buckets whose name is an MLS placeholder for "no selling agent recorded" (`non member`, `non listed agent`, and ~140 board-specific spellings) are excluded rather than ranked as agents — they are not people and cannot be resolved with `GET /v1/agents/{id}`. Percentages are shares of the company's whole loan population, so they do not sum to 100 across the page.
|
|
1986
2486
|
*/
|
|
1987
2487
|
static agents(options) {
|
|
@@ -1997,7 +2497,7 @@ var Companies = class {
|
|
|
1997
2497
|
...options,
|
|
1998
2498
|
headers: {
|
|
1999
2499
|
"Content-Type": "application/json",
|
|
2000
|
-
...options
|
|
2500
|
+
...options.headers
|
|
2001
2501
|
}
|
|
2002
2502
|
});
|
|
2003
2503
|
}
|
|
@@ -2017,7 +2517,7 @@ var Companies = class {
|
|
|
2017
2517
|
...options,
|
|
2018
2518
|
headers: {
|
|
2019
2519
|
"Content-Type": "application/json",
|
|
2020
|
-
...options
|
|
2520
|
+
...options.headers
|
|
2021
2521
|
}
|
|
2022
2522
|
});
|
|
2023
2523
|
}
|
|
@@ -2037,7 +2537,7 @@ var Companies = class {
|
|
|
2037
2537
|
...options,
|
|
2038
2538
|
headers: {
|
|
2039
2539
|
"Content-Type": "application/json",
|
|
2040
|
-
...options
|
|
2540
|
+
...options.headers
|
|
2041
2541
|
}
|
|
2042
2542
|
});
|
|
2043
2543
|
}
|
|
@@ -2057,7 +2557,7 @@ var Companies = class {
|
|
|
2057
2557
|
...options,
|
|
2058
2558
|
headers: {
|
|
2059
2559
|
"Content-Type": "application/json",
|
|
2060
|
-
...options
|
|
2560
|
+
...options.headers
|
|
2061
2561
|
}
|
|
2062
2562
|
});
|
|
2063
2563
|
}
|
|
@@ -2077,7 +2577,7 @@ var Companies = class {
|
|
|
2077
2577
|
...options,
|
|
2078
2578
|
headers: {
|
|
2079
2579
|
"Content-Type": "application/json",
|
|
2080
|
-
...options
|
|
2580
|
+
...options.headers
|
|
2081
2581
|
}
|
|
2082
2582
|
});
|
|
2083
2583
|
}
|
|
@@ -2097,12 +2597,13 @@ var Companies = class {
|
|
|
2097
2597
|
...options,
|
|
2098
2598
|
headers: {
|
|
2099
2599
|
"Content-Type": "application/json",
|
|
2100
|
-
...options
|
|
2600
|
+
...options.headers
|
|
2101
2601
|
}
|
|
2102
2602
|
});
|
|
2103
2603
|
}
|
|
2104
2604
|
/**
|
|
2105
2605
|
* Loan officers who originated through this company
|
|
2606
|
+
*
|
|
2106
2607
|
* Ranks the loan officers on this company's loans (scope with `roleScope` — `tpo` for its third-party originators). `label` is the LO's NMLS id; `name` and `company` (the LO's CURRENT employer per NMLS licensing, not necessarily the company on the loans) are resolved server-side, and are absent for an id with no originator profile. `sort: [{field: "name"}]` orders by that resolved name across the top 10,000 originators by volume (`truncated` says when there are more).
|
|
2107
2608
|
*/
|
|
2108
2609
|
static originators(options) {
|
|
@@ -2118,7 +2619,7 @@ var Companies = class {
|
|
|
2118
2619
|
...options,
|
|
2119
2620
|
headers: {
|
|
2120
2621
|
"Content-Type": "application/json",
|
|
2121
|
-
...options
|
|
2622
|
+
...options.headers
|
|
2122
2623
|
}
|
|
2123
2624
|
});
|
|
2124
2625
|
}
|
|
@@ -2138,12 +2639,13 @@ var Companies = class {
|
|
|
2138
2639
|
...options,
|
|
2139
2640
|
headers: {
|
|
2140
2641
|
"Content-Type": "application/json",
|
|
2141
|
-
...options
|
|
2642
|
+
...options.headers
|
|
2142
2643
|
}
|
|
2143
2644
|
});
|
|
2144
2645
|
}
|
|
2145
2646
|
/**
|
|
2146
2647
|
* Title companies on this company's loans (spellings merged)
|
|
2648
|
+
*
|
|
2147
2649
|
* Ranks the title companies on this entity's loans (recorded deeds, `recording_date` window — the same population and period axis as every other loans breakdown). Spellings of one company are MERGED: `label` is its most-used spelling, `id` the normalized name every spelling was grouped under (legal-form and filler words such as `inc`, `llc`, `co`, `company`, `title`, `escrow` removed; `natl` → `national`). Placeholder entries meaning "no title company recorded" (`none available` and its misspellings, `unknown`, `n/a`, …) and names shorter than 3 characters are excluded rather than ranked. `attorney` and `accommodation` are kept: they say who closed. `pctUnits` / `pctVolume` are shares of the entity's WHOLE loan population in the window, including loans with no title company, so they do not sum to 100 across the page. Pages of up to 100 via `pagination`.
|
|
2148
2650
|
*/
|
|
2149
2651
|
static titleCompanies(options) {
|
|
@@ -2159,7 +2661,7 @@ var Companies = class {
|
|
|
2159
2661
|
...options,
|
|
2160
2662
|
headers: {
|
|
2161
2663
|
"Content-Type": "application/json",
|
|
2162
|
-
...options
|
|
2664
|
+
...options.headers
|
|
2163
2665
|
}
|
|
2164
2666
|
});
|
|
2165
2667
|
}
|
|
@@ -2179,12 +2681,13 @@ var Companies = class {
|
|
|
2179
2681
|
...options,
|
|
2180
2682
|
headers: {
|
|
2181
2683
|
"Content-Type": "application/json",
|
|
2182
|
-
...options
|
|
2684
|
+
...options.headers
|
|
2183
2685
|
}
|
|
2184
2686
|
});
|
|
2185
2687
|
}
|
|
2186
2688
|
/**
|
|
2187
2689
|
* How many of a company's exits work elsewhere today
|
|
2690
|
+
*
|
|
2188
2691
|
* The window's complete departures, split by whether each loan officer's current employer on file is another company. One aggregate — no rows.
|
|
2189
2692
|
*/
|
|
2190
2693
|
static departureStatus(options) {
|
|
@@ -2234,6 +2737,7 @@ var Companies = class {
|
|
|
2234
2737
|
}
|
|
2235
2738
|
/**
|
|
2236
2739
|
* List a company's loan officers: current roster, hires, or exits
|
|
2740
|
+
*
|
|
2237
2741
|
* Loan officers employed by (sponsored or registered with) this company, one row per person, from NMLS employment records. `status` picks the current roster, the window's hires, the window's complete departures, or everyone; `asOf` gives the roster on a past date. Rows carry tenure dates, branch-manager status, branch location, current employer, contact details and period production.
|
|
2238
2742
|
*/
|
|
2239
2743
|
static employment(options) {
|
|
@@ -2267,6 +2771,7 @@ var Companies = class {
|
|
|
2267
2771
|
}
|
|
2268
2772
|
/**
|
|
2269
2773
|
* Where a company lends — blended market footprint
|
|
2774
|
+
*
|
|
2270
2775
|
* The company's market footprint for a period: a units-weighted summary, the ZIP-level markets, and the city / county / state rollups, computed from the company's recorded transactions. Optionally narrow to a set of ZIP codes and/or a custom date window. Shares are percentages on a 0–100 scale. The summary also carries a Community Lending mix — what kind of neighborhood the book lands in, as U.S. Census tract-level aggregates describing whole neighborhoods, never individual or applicant attributes. Unfiltered, it is the company's own whole-period mix; any ZIP, date or transaction filter recomputes it over the markets in scope, and `summary.communityLending.basis` says which you got.
|
|
2271
2776
|
*/
|
|
2272
2777
|
static markets(options) {
|
|
@@ -2282,12 +2787,13 @@ var Companies = class {
|
|
|
2282
2787
|
...options,
|
|
2283
2788
|
headers: {
|
|
2284
2789
|
"Content-Type": "application/json",
|
|
2285
|
-
...options
|
|
2790
|
+
...options.headers
|
|
2286
2791
|
}
|
|
2287
2792
|
});
|
|
2288
2793
|
}
|
|
2289
2794
|
/**
|
|
2290
2795
|
* Combined production of a company's hires and exits
|
|
2796
|
+
*
|
|
2291
2797
|
* The window's hires and complete departures, each side's combined production across ALL employers recorded inside the production window (default: the same window). Pass a prior window's movers with the current production window to see how past hires and exits perform now.
|
|
2292
2798
|
*/
|
|
2293
2799
|
static moverProduction(options) {
|
|
@@ -2319,7 +2825,7 @@ var Companies = class {
|
|
|
2319
2825
|
...options,
|
|
2320
2826
|
headers: {
|
|
2321
2827
|
"Content-Type": "application/json",
|
|
2322
|
-
...options
|
|
2828
|
+
...options.headers
|
|
2323
2829
|
}
|
|
2324
2830
|
});
|
|
2325
2831
|
}
|
|
@@ -2339,7 +2845,7 @@ var Companies = class {
|
|
|
2339
2845
|
...options,
|
|
2340
2846
|
headers: {
|
|
2341
2847
|
"Content-Type": "application/json",
|
|
2342
|
-
...options
|
|
2848
|
+
...options.headers
|
|
2343
2849
|
}
|
|
2344
2850
|
});
|
|
2345
2851
|
}
|
|
@@ -3081,12 +3587,13 @@ var Crm = class {
|
|
|
3081
3587
|
...options,
|
|
3082
3588
|
headers: {
|
|
3083
3589
|
"Content-Type": "application/json",
|
|
3084
|
-
...options
|
|
3590
|
+
...options.headers
|
|
3085
3591
|
}
|
|
3086
3592
|
});
|
|
3087
3593
|
}
|
|
3088
3594
|
/**
|
|
3089
3595
|
* Apply accepted Market-Insights updates to several list records
|
|
3596
|
+
*
|
|
3090
3597
|
* Bulk form of `applyCrmMiUpdates` for records in one CRM list: for each record, persist ONLY the updates listed for it (copy them from `getCrmListMiUpdates` — `store`, `field` or `kind`, and the `incoming` value as `value`). Never send updates the user did not accept. Proposals on a record that were not accepted count as reviewed. Records not in the list are reported, not applied.
|
|
3091
3598
|
*/
|
|
3092
3599
|
static applyCrmListMiUpdates(options) {
|
|
@@ -3102,7 +3609,7 @@ var Crm = class {
|
|
|
3102
3609
|
...options,
|
|
3103
3610
|
headers: {
|
|
3104
3611
|
"Content-Type": "application/json",
|
|
3105
|
-
...options
|
|
3612
|
+
...options.headers
|
|
3106
3613
|
}
|
|
3107
3614
|
});
|
|
3108
3615
|
}
|
|
@@ -3124,6 +3631,7 @@ var Crm = class {
|
|
|
3124
3631
|
}
|
|
3125
3632
|
/**
|
|
3126
3633
|
* Snooze Market-Insights updates on several list records
|
|
3634
|
+
*
|
|
3127
3635
|
* Bulk form of `dismissCrmMiUpdates` for records in one CRM list: marks the updates last shown for each record as reviewed for the 31-day check window, so `getCrmListMiUpdates` stops returning them. Nothing is written to the records. A proposal that was not shown yet (new Market-Insights data) still comes back.
|
|
3128
3636
|
*/
|
|
3129
3637
|
static dismissCrmListMiUpdates(options) {
|
|
@@ -3139,7 +3647,7 @@ var Crm = class {
|
|
|
3139
3647
|
...options,
|
|
3140
3648
|
headers: {
|
|
3141
3649
|
"Content-Type": "application/json",
|
|
3142
|
-
...options
|
|
3650
|
+
...options.headers
|
|
3143
3651
|
}
|
|
3144
3652
|
});
|
|
3145
3653
|
}
|
|
@@ -3159,7 +3667,7 @@ var Crm = class {
|
|
|
3159
3667
|
...options,
|
|
3160
3668
|
headers: {
|
|
3161
3669
|
"Content-Type": "application/json",
|
|
3162
|
-
...options
|
|
3670
|
+
...options.headers
|
|
3163
3671
|
}
|
|
3164
3672
|
});
|
|
3165
3673
|
}
|
|
@@ -3195,7 +3703,7 @@ var Crm = class {
|
|
|
3195
3703
|
...options,
|
|
3196
3704
|
headers: {
|
|
3197
3705
|
"Content-Type": "application/json",
|
|
3198
|
-
...options
|
|
3706
|
+
...options.headers
|
|
3199
3707
|
}
|
|
3200
3708
|
});
|
|
3201
3709
|
}
|
|
@@ -3215,7 +3723,7 @@ var Crm = class {
|
|
|
3215
3723
|
...options,
|
|
3216
3724
|
headers: {
|
|
3217
3725
|
"Content-Type": "application/json",
|
|
3218
|
-
...options
|
|
3726
|
+
...options.headers
|
|
3219
3727
|
}
|
|
3220
3728
|
});
|
|
3221
3729
|
}
|
|
@@ -3235,12 +3743,13 @@ var Crm = class {
|
|
|
3235
3743
|
...options,
|
|
3236
3744
|
headers: {
|
|
3237
3745
|
"Content-Type": "application/json",
|
|
3238
|
-
...options
|
|
3746
|
+
...options.headers
|
|
3239
3747
|
}
|
|
3240
3748
|
});
|
|
3241
3749
|
}
|
|
3242
3750
|
/**
|
|
3243
3751
|
* Find the records in a CRM list that have Market-Insights updates to review
|
|
3752
|
+
*
|
|
3244
3753
|
* Checks a CRM list's members against current Market-Insights data and returns ONLY the records that need attention, each with its proposed updates. Use this instead of calling `getCrmRecordProfile` + `getCrmMiUpdates` for every member: one call covers a page of up to 50 members, and records the user already reviewed (applied or dismissed) with nothing new since are left out. Page with `cursor` until `nextCursor` is null; a page may return no records and still have more to scan. Act on the results with `applyCrmListMiUpdates` (explicit per-record accepted updates) and `dismissCrmListMiUpdates` (snooze the rest). Each scan counts as a check of those records, exactly like `getCrmMiUpdates`.
|
|
3245
3754
|
*/
|
|
3246
3755
|
static getCrmListMiUpdates(options) {
|
|
@@ -3256,7 +3765,7 @@ var Crm = class {
|
|
|
3256
3765
|
...options,
|
|
3257
3766
|
headers: {
|
|
3258
3767
|
"Content-Type": "application/json",
|
|
3259
|
-
...options
|
|
3768
|
+
...options.headers
|
|
3260
3769
|
}
|
|
3261
3770
|
});
|
|
3262
3771
|
}
|
|
@@ -3292,7 +3801,7 @@ var Crm = class {
|
|
|
3292
3801
|
...options,
|
|
3293
3802
|
headers: {
|
|
3294
3803
|
"Content-Type": "application/json",
|
|
3295
|
-
...options
|
|
3804
|
+
...options.headers
|
|
3296
3805
|
}
|
|
3297
3806
|
});
|
|
3298
3807
|
}
|
|
@@ -3328,7 +3837,7 @@ var Crm = class {
|
|
|
3328
3837
|
...options,
|
|
3329
3838
|
headers: {
|
|
3330
3839
|
"Content-Type": "application/json",
|
|
3331
|
-
...options
|
|
3840
|
+
...options.headers
|
|
3332
3841
|
}
|
|
3333
3842
|
});
|
|
3334
3843
|
}
|
|
@@ -3348,7 +3857,7 @@ var Crm = class {
|
|
|
3348
3857
|
...options,
|
|
3349
3858
|
headers: {
|
|
3350
3859
|
"Content-Type": "application/json",
|
|
3351
|
-
...options
|
|
3860
|
+
...options.headers
|
|
3352
3861
|
}
|
|
3353
3862
|
});
|
|
3354
3863
|
}
|
|
@@ -3368,7 +3877,7 @@ var Crm = class {
|
|
|
3368
3877
|
...options,
|
|
3369
3878
|
headers: {
|
|
3370
3879
|
"Content-Type": "application/json",
|
|
3371
|
-
...options
|
|
3880
|
+
...options.headers
|
|
3372
3881
|
}
|
|
3373
3882
|
});
|
|
3374
3883
|
}
|
|
@@ -3388,7 +3897,7 @@ var Crm = class {
|
|
|
3388
3897
|
...options,
|
|
3389
3898
|
headers: {
|
|
3390
3899
|
"Content-Type": "application/json",
|
|
3391
|
-
...options
|
|
3900
|
+
...options.headers
|
|
3392
3901
|
}
|
|
3393
3902
|
});
|
|
3394
3903
|
}
|
|
@@ -3424,7 +3933,7 @@ var Crm = class {
|
|
|
3424
3933
|
...options,
|
|
3425
3934
|
headers: {
|
|
3426
3935
|
"Content-Type": "application/json",
|
|
3427
|
-
...options
|
|
3936
|
+
...options.headers
|
|
3428
3937
|
}
|
|
3429
3938
|
});
|
|
3430
3939
|
}
|
|
@@ -3444,7 +3953,7 @@ var Crm = class {
|
|
|
3444
3953
|
...options,
|
|
3445
3954
|
headers: {
|
|
3446
3955
|
"Content-Type": "application/json",
|
|
3447
|
-
...options
|
|
3956
|
+
...options.headers
|
|
3448
3957
|
}
|
|
3449
3958
|
});
|
|
3450
3959
|
}
|
|
@@ -4286,6 +4795,7 @@ var Crm = class {
|
|
|
4286
4795
|
}
|
|
4287
4796
|
/**
|
|
4288
4797
|
* Per-user, per-day activity counts with previous-period totals
|
|
4798
|
+
*
|
|
4289
4799
|
* Human actions only, attributed to the actor (never the record owner). `previousTotals` covers the equal-length period immediately before `from`. Ratios (connect rate, show rate, win rate) are client-side divisions.
|
|
4290
4800
|
*/
|
|
4291
4801
|
static getCrmActivityReport(options) {
|
|
@@ -4303,6 +4813,7 @@ var Crm = class {
|
|
|
4303
4813
|
}
|
|
4304
4814
|
/**
|
|
4305
4815
|
* Cohort outcomes: wins/losses, volume onboarded, milestones, effort per win, pipeline
|
|
4816
|
+
*
|
|
4306
4817
|
* Cohort = records that hit the event in [from, to). Win/loss resolves through each status option's `outcome` (seed ids `won`/`lost` by convention). `pipeline` is a current snapshot and ignores the range.
|
|
4307
4818
|
*/
|
|
4308
4819
|
static getCrmOutcomesReport(options) {
|
|
@@ -4534,7 +5045,7 @@ var Crm = class {
|
|
|
4534
5045
|
...options,
|
|
4535
5046
|
headers: {
|
|
4536
5047
|
"Content-Type": "application/json",
|
|
4537
|
-
...options
|
|
5048
|
+
...options.headers
|
|
4538
5049
|
}
|
|
4539
5050
|
});
|
|
4540
5051
|
}
|
|
@@ -4586,7 +5097,7 @@ var Crm = class {
|
|
|
4586
5097
|
...options,
|
|
4587
5098
|
headers: {
|
|
4588
5099
|
"Content-Type": "application/json",
|
|
4589
|
-
...options
|
|
5100
|
+
...options.headers
|
|
4590
5101
|
}
|
|
4591
5102
|
});
|
|
4592
5103
|
}
|
|
@@ -4594,6 +5105,7 @@ var Crm = class {
|
|
|
4594
5105
|
var Search = class {
|
|
4595
5106
|
/**
|
|
4596
5107
|
* Instant multi-entity typeahead search
|
|
5108
|
+
*
|
|
4597
5109
|
* Fast typeahead/autocomplete search across agents, originators, companies, and offices. Returns top matches per entity type. A bare NMLS ID resolves directly to its originator, company, or branch — including an originator who is in the NMLS registry with no production record yet (returned with `hasScoredData: false`). Use this for quick name lookups, not for filtered searches (use the entity-specific list endpoints for those). If you already have an entity ID, prefer getOriginator / getCompany / getBranch.
|
|
4598
5110
|
*/
|
|
4599
5111
|
static instant(options) {
|
|
@@ -4615,6 +5127,7 @@ var Search = class {
|
|
|
4615
5127
|
}
|
|
4616
5128
|
/**
|
|
4617
5129
|
* Mint a scoped search token
|
|
5130
|
+
*
|
|
4618
5131
|
* Returns a short-lived scoped search token plus the host to query, so a trusted client can search the entity indexes directly with per-query controls (e.g. attributesToSearchOn for name-only matching).
|
|
4619
5132
|
*/
|
|
4620
5133
|
static getSearchToken(options) {
|
|
@@ -4634,6 +5147,7 @@ var Search = class {
|
|
|
4634
5147
|
var Integrations = class {
|
|
4635
5148
|
/**
|
|
4636
5149
|
* Send records to your HubSpot account
|
|
5150
|
+
*
|
|
4637
5151
|
* Sends the given Model Match records into the HubSpot account you have connected, using the field mapping your workspace configured. Existing records are matched and updated rather than duplicated, so sending the same list twice does not create it twice. Every id you send comes back with an outcome — some records failing is normal and does not fail the rest. At most 100 records per request; send larger lists in batches. There is no undo: use `dryRun` first to see exactly what would be written. Charged per record actually written, at the same rate as fetching that record.
|
|
4638
5152
|
*/
|
|
4639
5153
|
static pushToHubspot(options) {
|
|
@@ -4655,6 +5169,7 @@ var Integrations = class {
|
|
|
4655
5169
|
}
|
|
4656
5170
|
/**
|
|
4657
5171
|
* Check whether records can be sent to HubSpot
|
|
5172
|
+
*
|
|
4658
5173
|
* Reports whether your HubSpot account is connected, which record types your workspace has set up to send, and whether the connected account is the one that setup was built for. Read-only — call it before offering to send anything.
|
|
4659
5174
|
*/
|
|
4660
5175
|
static getHubspotPushStatus(options) {
|
|
@@ -4674,6 +5189,7 @@ var Integrations = class {
|
|
|
4674
5189
|
var Lenders = class {
|
|
4675
5190
|
/**
|
|
4676
5191
|
* Search lenders with filters
|
|
5192
|
+
*
|
|
4677
5193
|
* Search and list normalized lender names/identities with filters — resolves raw or variant lender names to canonical lender records. Use it to look up a lender by name or reconcile lender-name variants to a single canonical entity. If you only need how many lenders match and not the records themselves, send the same request body to `countLenders`.
|
|
4678
5194
|
*/
|
|
4679
5195
|
static list(options) {
|
|
@@ -4695,6 +5211,7 @@ var Lenders = class {
|
|
|
4695
5211
|
}
|
|
4696
5212
|
/**
|
|
4697
5213
|
* Count lenders matching filters
|
|
5214
|
+
*
|
|
4698
5215
|
* Return the exact number of lenders matching the given filters. Accepts the same request body as `listLenders` (pagination and sort are ignored). Use this when you only need a total; to get the matching lenders themselves, send the same request body to `listLenders`.
|
|
4699
5216
|
*/
|
|
4700
5217
|
static count(options) {
|
|
@@ -4732,6 +5249,7 @@ var Lenders = class {
|
|
|
4732
5249
|
}
|
|
4733
5250
|
/**
|
|
4734
5251
|
* City volume breakdown across this lender's loans
|
|
5252
|
+
*
|
|
4735
5253
|
* Ranks the cities this lender's loans were secured in, by volume. Labels are Title Case so they match the city breakdowns on every other entity.
|
|
4736
5254
|
*/
|
|
4737
5255
|
static cities(options) {
|
|
@@ -4747,12 +5265,13 @@ var Lenders = class {
|
|
|
4747
5265
|
...options,
|
|
4748
5266
|
headers: {
|
|
4749
5267
|
"Content-Type": "application/json",
|
|
4750
|
-
...options
|
|
5268
|
+
...options.headers
|
|
4751
5269
|
}
|
|
4752
5270
|
});
|
|
4753
5271
|
}
|
|
4754
5272
|
/**
|
|
4755
5273
|
* Mortgage companies that send business to this lender
|
|
5274
|
+
*
|
|
4756
5275
|
* Ranks the mortgage companies whose loans funded through this lender, by volume. Each label is the company's NMLS ID (with the company name resolved alongside it where available), so it chains straight into `GET /v1/companies/{nmlsId}`. Loans with no identified company are excluded.
|
|
4757
5276
|
*/
|
|
4758
5277
|
static companies(options) {
|
|
@@ -4768,12 +5287,13 @@ var Lenders = class {
|
|
|
4768
5287
|
...options,
|
|
4769
5288
|
headers: {
|
|
4770
5289
|
"Content-Type": "application/json",
|
|
4771
|
-
...options
|
|
5290
|
+
...options.headers
|
|
4772
5291
|
}
|
|
4773
5292
|
});
|
|
4774
5293
|
}
|
|
4775
5294
|
/**
|
|
4776
5295
|
* County volume breakdown across this lender's loans
|
|
5296
|
+
*
|
|
4777
5297
|
* Ranks the counties this lender's loans were secured in, by volume. Labels are county codes on this surface — the same axis every other county breakdown uses, so the two are directly comparable.
|
|
4778
5298
|
*/
|
|
4779
5299
|
static counties(options) {
|
|
@@ -4789,12 +5309,13 @@ var Lenders = class {
|
|
|
4789
5309
|
...options,
|
|
4790
5310
|
headers: {
|
|
4791
5311
|
"Content-Type": "application/json",
|
|
4792
|
-
...options
|
|
5312
|
+
...options.headers
|
|
4793
5313
|
}
|
|
4794
5314
|
});
|
|
4795
5315
|
}
|
|
4796
5316
|
/**
|
|
4797
5317
|
* Loan officers who send business to this lender
|
|
5318
|
+
*
|
|
4798
5319
|
* Ranks the loan officers whose loans funded through this lender, by volume. Each label is the loan officer's NMLS ID, so it chains straight into `GET /v1/originators/{nmlsId}`. Loans with no identified loan officer are excluded rather than collapsed into one unnavigable bucket.
|
|
4799
5320
|
*/
|
|
4800
5321
|
static originators(options) {
|
|
@@ -4810,12 +5331,13 @@ var Lenders = class {
|
|
|
4810
5331
|
...options,
|
|
4811
5332
|
headers: {
|
|
4812
5333
|
"Content-Type": "application/json",
|
|
4813
|
-
...options
|
|
5334
|
+
...options.headers
|
|
4814
5335
|
}
|
|
4815
5336
|
});
|
|
4816
5337
|
}
|
|
4817
5338
|
/**
|
|
4818
5339
|
* State volume breakdown across this lender's loans
|
|
5340
|
+
*
|
|
4819
5341
|
* Ranks the states this lender's loans were secured in, by volume. Labels are two-letter state abbreviations.
|
|
4820
5342
|
*/
|
|
4821
5343
|
static states(options) {
|
|
@@ -4831,7 +5353,7 @@ var Lenders = class {
|
|
|
4831
5353
|
...options,
|
|
4832
5354
|
headers: {
|
|
4833
5355
|
"Content-Type": "application/json",
|
|
4834
|
-
...options
|
|
5356
|
+
...options.headers
|
|
4835
5357
|
}
|
|
4836
5358
|
});
|
|
4837
5359
|
}
|
|
@@ -4839,6 +5361,7 @@ var Lenders = class {
|
|
|
4839
5361
|
var Loans = class {
|
|
4840
5362
|
/**
|
|
4841
5363
|
* Search individual loan records with filters
|
|
5364
|
+
*
|
|
4842
5365
|
* Search and list individual public-record mortgage and deed loan records — one row per loan (purchase, refinance, origination). Filter by geography (state, county, city, zip), lender, originator, loan amount, interest rate, loan type/purpose, and recording date, with sorting and cursor pagination. This is the discrete per-loan record search: use it to find specific loans or build a filtered loan list. Each row carries the property address, loan terms, the originating loan officer, and `borrowerStatus` — so this is also how you pull a loan officer's own funded production ("my closed loans", "my past clients", "my book of business"): filter by `originator` (their NMLS id), and add `borrowerStatus` for borrowers still in the home — that is the five current-owner codes (`Current`, `R_CWCLO`, `R_CWNLO`, `E_CWCLO`, `E_CWNLO`), NOT `"Current"` alone, which omits everyone who has since refinanced. That is market data, not CRM data — it does not require the loan officer to have added anything to a CRM workspace. (For aggregate market rates and volumes use the market search; for one loan by its ID use the loan detail endpoint.) If you only need how many loans match and not the records themselves, send the same request body to `countLoans`.
|
|
4843
5366
|
*/
|
|
4844
5367
|
static list(options) {
|
|
@@ -4860,6 +5383,7 @@ var Loans = class {
|
|
|
4860
5383
|
}
|
|
4861
5384
|
/**
|
|
4862
5385
|
* Configurable chart data (measure × slice)
|
|
5386
|
+
*
|
|
4863
5387
|
* Buckets the filtered loans by `slice` and ranks them by `measure`, descending. Party slices (`originator`, `broker`, `loanCompany`) are pageable: send `size` (1–1000) and follow `nextCursor` via `after` to walk the whole ranking, with `total` giving the (approximate) number of distinct parties. Other slices return their fixed top-N. `period` accepts rolling windows (`last30Days`, `last60Days`, `last90Days`, `previousMonth`, `currentMonth`) resolved in UTC; `/loans/analytics/summary` with the same filters and period returns the matching population totals.
|
|
4864
5388
|
*/
|
|
4865
5389
|
static analyticsChart(options) {
|
|
@@ -4921,6 +5445,7 @@ var Loans = class {
|
|
|
4921
5445
|
}
|
|
4922
5446
|
/**
|
|
4923
5447
|
* Submit a bulk-delivery job for loans
|
|
5448
|
+
*
|
|
4924
5449
|
* Queues an ECS task that dumps every matching loans document to S3 in the requested format. Returns 202 with a jobId; poll `GET /v1/loans/bulk-delivery/{jobId}` for status + the signed download URL.
|
|
4925
5450
|
*
|
|
4926
5451
|
* **Row limit.** Deliveries of up to 5,000 rows need no entitlement. Above that, the org's `bulk-delivery.loans` entitlement is required and its scope (row ceiling, row filters, allowed fields) governs the delivery; without it the request is rejected with 403 `entitlement_missing`. Pass `limit` at or below the ceiling to deliver a capped subset of a broader query. Email support@modelmatch.com to request a limit increase.
|
|
@@ -4948,6 +5473,7 @@ var Loans = class {
|
|
|
4948
5473
|
}
|
|
4949
5474
|
/**
|
|
4950
5475
|
* Cancel a bulk-delivery job for loans
|
|
5476
|
+
*
|
|
4951
5477
|
* Cancels a queued or running loans delivery job.
|
|
4952
5478
|
*
|
|
4953
5479
|
* The job is marked `cancelled` immediately; the container running it notices on its next page boundary and stops. Because a delivery is billed once, at the end, **a cancelled job is never charged** — no credits are debited and there is nothing to refund. No partial file is written.
|
|
@@ -4985,6 +5511,7 @@ var Loans = class {
|
|
|
4985
5511
|
}
|
|
4986
5512
|
/**
|
|
4987
5513
|
* Count loans matching filters
|
|
5514
|
+
*
|
|
4988
5515
|
* Return the exact number of loans matching the given filters. Accepts the same request body as `listLoans` (pagination and sort are ignored). Use this when you only need a total; to get the matching loans themselves, send the same request body to `listLoans`.
|
|
4989
5516
|
*/
|
|
4990
5517
|
static count(options) {
|
|
@@ -5024,6 +5551,7 @@ var Loans = class {
|
|
|
5024
5551
|
var Locations = class {
|
|
5025
5552
|
/**
|
|
5026
5553
|
* Retrieve normalized location details
|
|
5554
|
+
*
|
|
5027
5555
|
* Retrieve normalized location details (city, state, county, zip, coordinates) for a suggestion ID from `suggestLocations`. A location dictionary id resolves from Model Match's own data and echoes back its `id`; any other id resolves through Mapbox.
|
|
5028
5556
|
*/
|
|
5029
5557
|
static retrieve(options) {
|
|
@@ -5041,6 +5569,7 @@ var Locations = class {
|
|
|
5041
5569
|
}
|
|
5042
5570
|
/**
|
|
5043
5571
|
* Autocomplete location search
|
|
5572
|
+
*
|
|
5044
5573
|
* Autocomplete location search. Cities and counties come from Model Match's own location dictionary and carry an `id` (e.g. `city_mo_saint-louis`) that city / county filters accept — including for places our data spells differently than a mapping provider does. Street addresses come from Mapbox. Use the `mapbox_id` from any suggestion with `retrieveLocation` to get normalized geographic details and coordinates.
|
|
5045
5574
|
*/
|
|
5046
5575
|
static suggest(options) {
|
|
@@ -5060,6 +5589,7 @@ var Locations = class {
|
|
|
5060
5589
|
var Market = class {
|
|
5061
5590
|
/**
|
|
5062
5591
|
* Search aggregated market data with filters
|
|
5592
|
+
*
|
|
5063
5593
|
* Search aggregated loan origination market data. Filterable dimensions cover geography (state, county, zip), product (loan purpose / type / amortization), borrower demographics, and loan numerics.
|
|
5064
5594
|
*/
|
|
5065
5595
|
static list(options) {
|
|
@@ -5141,6 +5671,7 @@ var Market = class {
|
|
|
5141
5671
|
}
|
|
5142
5672
|
/**
|
|
5143
5673
|
* Community Lending mix of a market's originations
|
|
5674
|
+
*
|
|
5144
5675
|
* The aggregate Community Lending profile of the originations matching your filters: the share that landed in low- or moderate-income neighborhoods, the CRA-eligible share, the distribution across the four neighborhood income bands, and the majority-minority neighborhood share. Values describe the U.S. Census tract (neighborhood) as a whole — tract-level aggregate statistics, never an individual, household or applicant attribute. Percentages are 0-100. This is a MARKET-LEVEL view only — the underlying origination data carries no lender, loan officer or borrower identity, and no figure here is attributable to one. Every share is reported next to the count it is a share of, because the three designations have three different coverage levels; read the denominator before comparing markets.
|
|
5145
5676
|
*/
|
|
5146
5677
|
static communityLending(options) {
|
|
@@ -5162,6 +5693,7 @@ var Market = class {
|
|
|
5162
5693
|
}
|
|
5163
5694
|
/**
|
|
5164
5695
|
* Monthly NMLS activity: newly licensed, active, leaving
|
|
5696
|
+
*
|
|
5165
5697
|
* Monthly series of newly licensed loan officers, loan officers with an open employment at month end, and loan officers who left the industry (no open employment; last one ended that month). `becameInactive` (license authorization lapses) is not available and is always null. `all_time` charts the last 60 months. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5166
5698
|
*/
|
|
5167
5699
|
static movementActivity(options) {
|
|
@@ -5179,6 +5711,7 @@ var Market = class {
|
|
|
5179
5711
|
}
|
|
5180
5712
|
/**
|
|
5181
5713
|
* Loan officer movement by state and city
|
|
5714
|
+
*
|
|
5182
5715
|
* Loan officers who changed companies in the window, grouped by state (all states) and city (top `limit`), each with the company that gained the most of them. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5183
5716
|
*/
|
|
5184
5717
|
static movementByState(options) {
|
|
@@ -5196,6 +5729,7 @@ var Market = class {
|
|
|
5196
5729
|
}
|
|
5197
5730
|
/**
|
|
5198
5731
|
* Did the move pay off? Production before vs after moving
|
|
5732
|
+
*
|
|
5199
5733
|
* For loan officers who moved in the window (default last 24 months), annualized production at the previous employer vs the new one, bucketed by pre-move tier (Low <25, Mid 25–99, High 100+ units/yr). Each side is annualized over the months actually spent there inside a trailing 24-month production window; movers with fewer than `windowMonths` months on either side are excluded. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5200
5734
|
*/
|
|
5201
5735
|
static movementCohortPayoff(options) {
|
|
@@ -5213,6 +5747,7 @@ var Market = class {
|
|
|
5213
5747
|
}
|
|
5214
5748
|
/**
|
|
5215
5749
|
* Companies that gained the most loan officers
|
|
5750
|
+
*
|
|
5216
5751
|
* Companies ranked by loan officers gained in the window (or by net = gained − lost with `rankBy=net`). Each row carries gained, lost and net, plus the trailing-14-month production of the loan officers on the ranked side. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5217
5752
|
*/
|
|
5218
5753
|
static movementMostGained(options) {
|
|
@@ -5230,6 +5765,7 @@ var Market = class {
|
|
|
5230
5765
|
}
|
|
5231
5766
|
/**
|
|
5232
5767
|
* Companies that lost the most loan officers
|
|
5768
|
+
*
|
|
5233
5769
|
* Companies ranked by loan officers lost in the window (or by net = gained − lost with `rankBy=net`). Each row carries gained, lost and net, plus the trailing-14-month production of the loan officers on the ranked side. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5234
5770
|
*/
|
|
5235
5771
|
static movementMostLost(options) {
|
|
@@ -5247,6 +5783,7 @@ var Market = class {
|
|
|
5247
5783
|
}
|
|
5248
5784
|
/**
|
|
5249
5785
|
* Loan officers who changed companies
|
|
5786
|
+
*
|
|
5250
5787
|
* The loan officers who moved to a new company in the window, with previous and new employer, move date, current location and production. `sort=volume` returns the highest producers who moved (notable moves); `sort=date` pages every move newest first. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5251
5788
|
*/
|
|
5252
5789
|
static movementMovers(options) {
|
|
@@ -5264,6 +5801,7 @@ var Market = class {
|
|
|
5264
5801
|
}
|
|
5265
5802
|
/**
|
|
5266
5803
|
* Top-100 loan officer rankings for a year
|
|
5804
|
+
*
|
|
5267
5805
|
* The top 100 loan officers for a calendar year by total volume, units, or FHA / VA / purchase / refinance volume, with current employer and retail / banker / broker type. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5268
5806
|
*/
|
|
5269
5807
|
static movementRankings(options) {
|
|
@@ -5281,6 +5819,7 @@ var Market = class {
|
|
|
5281
5819
|
}
|
|
5282
5820
|
/**
|
|
5283
5821
|
* Loan officer movement totals for a period
|
|
5822
|
+
*
|
|
5284
5823
|
* Period totals of loan-officer movement: company joins, company-to-company transitions, complete company departures, industry exits, newly licensed loan officers, the working head-count at both ends of the window and its net change, plus the trailing-14-month production of the loan officers who moved. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5285
5824
|
*/
|
|
5286
5825
|
static movementStats(options) {
|
|
@@ -5298,6 +5837,7 @@ var Market = class {
|
|
|
5298
5837
|
}
|
|
5299
5838
|
/**
|
|
5300
5839
|
* Company-to-company loan officer flows
|
|
5840
|
+
*
|
|
5301
5841
|
* The largest company-to-company flows in the window: how many loan officers moved from each previous employer to each new one. Filter to one company (either side) with `companyNmlsId`. A move is dated by the loan officer's FIRST record at the new company; a loan officer licensed in several states counts once per company. Location filters use the loan officer's CURRENT NMLS location. Results refresh weekly. A response not ready within 25 s answers `202` (`MovementComputing`): repeat the same request after `retryAfterMs`.
|
|
5302
5842
|
*/
|
|
5303
5843
|
static movementTransitions(options) {
|
|
@@ -5317,6 +5857,7 @@ var Market = class {
|
|
|
5317
5857
|
var Me = class {
|
|
5318
5858
|
/**
|
|
5319
5859
|
* Get the current caller's account
|
|
5860
|
+
*
|
|
5320
5861
|
* Identity, active organization + membership role, and how the caller authenticated.
|
|
5321
5862
|
*
|
|
5322
5863
|
* Extended profile fields (`nmlsId`, `jobRole`, the contact-card block) are resolved for every caller type — session-cookie, API-key, and OAuth-bearer alike. `auth.profileResolved` is `true` on any successful read; it is retained for compatibility and no longer varies by the credential the caller presented.
|
|
@@ -5336,6 +5877,7 @@ var Me = class {
|
|
|
5336
5877
|
}
|
|
5337
5878
|
/**
|
|
5338
5879
|
* Update the current caller's profile
|
|
5880
|
+
*
|
|
5339
5881
|
* Partial update — send only the fields that change; `null` clears one. Returns the account in the same shape as `GET /v1/me`.
|
|
5340
5882
|
*
|
|
5341
5883
|
* `email` is NOT updatable here: changing it runs a verification flow. Sending it is a 400, not a silent no-op.
|
|
@@ -5359,6 +5901,7 @@ var Me = class {
|
|
|
5359
5901
|
}
|
|
5360
5902
|
/**
|
|
5361
5903
|
* Get the caller's credit balance and usage
|
|
5904
|
+
*
|
|
5362
5905
|
* Balance split by bucket (cycle allowance, purchased on-demand, personal), the per-cycle allowance and on-demand unit price, and ledger totals over a window.
|
|
5363
5906
|
*
|
|
5364
5907
|
* The window defaults to the current calendar month to date (UTC). Figures are for the caller's own membership in their active organization — the same organization the API meters requests against.
|
|
@@ -5378,6 +5921,7 @@ var Me = class {
|
|
|
5378
5921
|
}
|
|
5379
5922
|
/**
|
|
5380
5923
|
* Get the caller's current plan
|
|
5924
|
+
*
|
|
5381
5925
|
* The active organization's resolved plan (with its limit map), the subscription status backing it, and the plan grants attached to the organization and to the user.
|
|
5382
5926
|
*
|
|
5383
5927
|
* `plan` is null when the workspace has no active, trialing, or past-due subscription. No billing details (invoices, payment methods) are exposed.
|
|
@@ -5399,6 +5943,7 @@ var Me = class {
|
|
|
5399
5943
|
var Offices = class {
|
|
5400
5944
|
/**
|
|
5401
5945
|
* Search real-estate offices with filters
|
|
5946
|
+
*
|
|
5402
5947
|
* NOT NMLS mortgage branches — use `/branches` for those. Returns office name, address, agent count, coordinates, and office-level production for the selected period. Default sort is by agent count descending. If you only need how many offices match and not the records themselves, send the same request body to `countOffices`.
|
|
5403
5948
|
*/
|
|
5404
5949
|
static list(options) {
|
|
@@ -5440,6 +5985,7 @@ var Offices = class {
|
|
|
5440
5985
|
}
|
|
5441
5986
|
/**
|
|
5442
5987
|
* Count offices matching filters
|
|
5988
|
+
*
|
|
5443
5989
|
* Return the exact number of offices matching the given filters. Accepts the same request body as `listOffices` (pagination and sort are ignored). Use this when you only need a total; to get the matching offices themselves, send the same request body to `listOffices`.
|
|
5444
5990
|
*/
|
|
5445
5991
|
static count(options) {
|
|
@@ -5461,6 +6007,7 @@ var Offices = class {
|
|
|
5461
6007
|
}
|
|
5462
6008
|
/**
|
|
5463
6009
|
* Office-name typeahead (distinct names with agent totals)
|
|
6010
|
+
*
|
|
5464
6011
|
* Distinct real-estate office names starting with `query`, each with the agents and offices behind that name across all its offices — the picker for filters that match by office name (`listOffices` `company`, `listAgents` `currentOffice`). To find one office, use `instantSearch` or `listOffices` instead.
|
|
5465
6012
|
*/
|
|
5466
6013
|
static suggestOfficeNames(options) {
|
|
@@ -5498,6 +6045,7 @@ var Offices = class {
|
|
|
5498
6045
|
}
|
|
5499
6046
|
/**
|
|
5500
6047
|
* Home builders on the office's deals (pre-aggregated)
|
|
6048
|
+
*
|
|
5501
6049
|
* New-construction builders named on the office's deals in the period, ranked by units. Spellings of one builder (case, punctuation, legal suffixes, a trailing "of <State>", generic words such as Homes, letter typos) are one row with `units` summed; distinct companies stay separate. Feed placeholders ("Unknown", "N/A", "-", "TBD", …) are dropped. Deal COUNT only: every row's `volume` / `pctVolume` is 0 and `pctUnits` is a share of ALL the office's deals. No buyer/listing split: `side` must be `any` (or omitted).
|
|
5502
6050
|
*/
|
|
5503
6051
|
static builders(options) {
|
|
@@ -5513,12 +6061,13 @@ var Offices = class {
|
|
|
5513
6061
|
...options,
|
|
5514
6062
|
headers: {
|
|
5515
6063
|
"Content-Type": "application/json",
|
|
5516
|
-
...options
|
|
6064
|
+
...options.headers
|
|
5517
6065
|
}
|
|
5518
6066
|
});
|
|
5519
6067
|
}
|
|
5520
6068
|
/**
|
|
5521
6069
|
* Lenders on the office's deals (pre-aggregated)
|
|
6070
|
+
*
|
|
5522
6071
|
* Lenders that financed the office's deals in the period. `id` is the lender id (pass it back as the `lender` filter on the loans routes), `label` its display name. The row for deals with no lender attributed carries no `id`.
|
|
5523
6072
|
*/
|
|
5524
6073
|
static lenders(options) {
|
|
@@ -5534,12 +6083,13 @@ var Offices = class {
|
|
|
5534
6083
|
...options,
|
|
5535
6084
|
headers: {
|
|
5536
6085
|
"Content-Type": "application/json",
|
|
5537
|
-
...options
|
|
6086
|
+
...options.headers
|
|
5538
6087
|
}
|
|
5539
6088
|
});
|
|
5540
6089
|
}
|
|
5541
6090
|
/**
|
|
5542
6091
|
* Loan products on the office's financed deals (pre-aggregated)
|
|
6092
|
+
*
|
|
5543
6093
|
* The office's financed deals in the period by loan product (`label` = product key, e.g. `conventional`, `fha`, `va`), summed across its lenders. Shares are of the financed deals on the requested side, so rows sum to 1; cash deals are not counted.
|
|
5544
6094
|
*/
|
|
5545
6095
|
static loanTypes(options) {
|
|
@@ -5555,12 +6105,13 @@ var Offices = class {
|
|
|
5555
6105
|
...options,
|
|
5556
6106
|
headers: {
|
|
5557
6107
|
"Content-Type": "application/json",
|
|
5558
|
-
...options
|
|
6108
|
+
...options.headers
|
|
5559
6109
|
}
|
|
5560
6110
|
});
|
|
5561
6111
|
}
|
|
5562
6112
|
/**
|
|
5563
6113
|
* Loan officers the office's agents worked with (pre-aggregated)
|
|
6114
|
+
*
|
|
5564
6115
|
* Loan officers on the office's deals in the period. `id` is the LO's NMLS id; `label` their registered name and `company` their current employer (both from the LO's own profile, not the deal records). `side: buyer` = deals where this office represented the buyer.
|
|
5565
6116
|
*/
|
|
5566
6117
|
static originators(options) {
|
|
@@ -5576,7 +6127,7 @@ var Offices = class {
|
|
|
5576
6127
|
...options,
|
|
5577
6128
|
headers: {
|
|
5578
6129
|
"Content-Type": "application/json",
|
|
5579
|
-
...options
|
|
6130
|
+
...options.headers
|
|
5580
6131
|
}
|
|
5581
6132
|
});
|
|
5582
6133
|
}
|
|
@@ -5584,6 +6135,7 @@ var Offices = class {
|
|
|
5584
6135
|
var Originators = class {
|
|
5585
6136
|
/**
|
|
5586
6137
|
* Search originators with filters
|
|
6138
|
+
*
|
|
5587
6139
|
* Search and list individual loan originators (LOs — NMLS-registered mortgage loan officers) with filters — one row per originator. Filter by name, NMLS ID, location (state, city), employer/company, and production metrics (loan volume, units, product mix), with sorting and cursor pagination. LOCATION SEMANTICS: the state/city filters match an originator's PRODUCTION GEOGRAPHY — the markets where they actually originated loans in the selected period — not where their office or employer sits. An LO who lends across several markets matches a filter for ANY of those markets, while the `state`/`city` returned on each row reflect only their PRIMARY (highest-volume) market. So a search for city "Long Beach" can return an LO whose displayed location is a different city/state (e.g. their top market is in Arizona) — they still originated loans in Long Beach, it just isn't their #1 market. To rank originators by their volume within a specific market, sort by volume after filtering, or use the per-originator city/county/state breakdown endpoints. NEWLY LICENSED / NO PRODUCTION: an originator who is in the NMLS registry but has no production record is returned only by an identity search — `nmlsId`, `name` or `namePrefix` as the ONLY filter — sent with `producersOnly: false`. Those rows come after the rows that have production, carry `hasScoredData: false`, and have `null` production fields. Under any other filter, or without `producersOnly: false`, they are not returned (use `getOriginator` for one by NMLS id). This is the per-originator record search: use it to find specific loan officers or build a filtered LO list. (For a single originator by NMLS ID use the originator detail endpoint.) If you only need how many originators match and not the records themselves, send the same request body to `countOriginators`.
|
|
5588
6140
|
*/
|
|
5589
6141
|
static list(options) {
|
|
@@ -5665,6 +6217,7 @@ var Originators = class {
|
|
|
5665
6217
|
}
|
|
5666
6218
|
/**
|
|
5667
6219
|
* Submit a bulk-delivery job for originators
|
|
6220
|
+
*
|
|
5668
6221
|
* Queues an ECS task that dumps every matching originators document to S3 in the requested format. Returns 202 with a jobId; poll `GET /v1/originators/bulk-delivery/{jobId}` for status + the signed download URL.
|
|
5669
6222
|
*
|
|
5670
6223
|
* **Row limit.** Deliveries of up to 5,000 rows need no entitlement. Above that, the org's `bulk-delivery.originators` entitlement is required and its scope (row ceiling, row filters, allowed fields) governs the delivery; without it the request is rejected with 403 `entitlement_missing`. Pass `limit` at or below the ceiling to deliver a capped subset of a broader query. Email support@modelmatch.com to request a limit increase.
|
|
@@ -5692,6 +6245,7 @@ var Originators = class {
|
|
|
5692
6245
|
}
|
|
5693
6246
|
/**
|
|
5694
6247
|
* Cancel a bulk-delivery job for originators
|
|
6248
|
+
*
|
|
5695
6249
|
* Cancels a queued or running originators delivery job.
|
|
5696
6250
|
*
|
|
5697
6251
|
* The job is marked `cancelled` immediately; the container running it notices on its next page boundary and stops. Because a delivery is billed once, at the end, **a cancelled job is never charged** — no credits are debited and there is nothing to refund. No partial file is written.
|
|
@@ -5729,6 +6283,7 @@ var Originators = class {
|
|
|
5729
6283
|
}
|
|
5730
6284
|
/**
|
|
5731
6285
|
* Submit contact details for a loan officer
|
|
6286
|
+
*
|
|
5732
6287
|
* Send contact details you know for a loan officer — a phone number, an email address, a profile link, or the company they moved to. The submission is checked and reviewed before anything appears on the profile; this call only records it and answers immediately. Sending the same details for the same person again while the first submission is still being reviewed returns the first submission's `id`.
|
|
5733
6288
|
*/
|
|
5734
6289
|
static createOriginatorContactSubmission(options) {
|
|
@@ -5750,6 +6305,7 @@ var Originators = class {
|
|
|
5750
6305
|
}
|
|
5751
6306
|
/**
|
|
5752
6307
|
* Count originators matching filters
|
|
6308
|
+
*
|
|
5753
6309
|
* Return the exact number of originators matching the given filters. Accepts the same request body as `listOriginators` (pagination and sort are ignored). Use this when you only need a total; to get the matching originators themselves, send the same request body to `listOriginators`.
|
|
5754
6310
|
*/
|
|
5755
6311
|
static count(options) {
|
|
@@ -5787,6 +6343,7 @@ var Originators = class {
|
|
|
5787
6343
|
}
|
|
5788
6344
|
/**
|
|
5789
6345
|
* Real-estate agents this LO co-closed with
|
|
6346
|
+
*
|
|
5790
6347
|
* Ranks the real-estate agents on this LO's loans, by volume — the buyer's agent by default, the listing and co-listing agents with `side: "listing"`. Each loan is credited to the agent its MLS agent keys resolve to (a key naming several different people credits only the confirmed one), so `units` counts distinct loans per agent. `id` is that agent's id (pass it to `GET /v1/agents/{id}`); absent when the loan's key matches no agent profile, in which case `label` is the name the MLS recorded. Names that are an MLS placeholder for "no agent recorded" (`non member`, `non listed agent`, and ~140 board-specific spellings) are excluded — they are not people. Percentages are shares of the LO's whole loan population, so they do not sum to 100 across the page.
|
|
5791
6348
|
*/
|
|
5792
6349
|
static agents(options) {
|
|
@@ -5802,7 +6359,7 @@ var Originators = class {
|
|
|
5802
6359
|
...options,
|
|
5803
6360
|
headers: {
|
|
5804
6361
|
"Content-Type": "application/json",
|
|
5805
|
-
...options
|
|
6362
|
+
...options.headers
|
|
5806
6363
|
}
|
|
5807
6364
|
});
|
|
5808
6365
|
}
|
|
@@ -5822,7 +6379,7 @@ var Originators = class {
|
|
|
5822
6379
|
...options,
|
|
5823
6380
|
headers: {
|
|
5824
6381
|
"Content-Type": "application/json",
|
|
5825
|
-
...options
|
|
6382
|
+
...options.headers
|
|
5826
6383
|
}
|
|
5827
6384
|
});
|
|
5828
6385
|
}
|
|
@@ -5842,12 +6399,13 @@ var Originators = class {
|
|
|
5842
6399
|
...options,
|
|
5843
6400
|
headers: {
|
|
5844
6401
|
"Content-Type": "application/json",
|
|
5845
|
-
...options
|
|
6402
|
+
...options.headers
|
|
5846
6403
|
}
|
|
5847
6404
|
});
|
|
5848
6405
|
}
|
|
5849
6406
|
/**
|
|
5850
6407
|
* Home builders on this LO's new-construction loans
|
|
6408
|
+
*
|
|
5851
6409
|
* Ranks the home builders behind this LO's new-construction loans, by volume. A loan counts when `originatorLoans` with `flatFilters.hasBuilder: true` keeps it, and is credited to the `builderName` that list shows on its row (the parcel's newest builder-named sale, else the builder named on the loan or its builder seller of record) — so a row's `units` equals that list's rows naming any of the builder's spellings. Spellings of one builder are one row (case, punctuation, legal suffixes such as LLC/LP, a trailing "of <State>", generic words such as Homes, and letter typos), with `units` and `volume` summed; `label` is the most common spelling and `id` its normalized key. Distinct companies (a builder's subsidiaries) stay separate rows. Feed placeholders ("Unknown", "N/A", "-", "TBD", …) are not builders: their loans get no row. Percentages are shares of the LO's whole loan population in scope, so rows do not sum to 100. More than 50,000 loans in scope is a 400 (narrow the period); `truncated` is set when the builder loans exceed that cap.
|
|
5852
6410
|
*/
|
|
5853
6411
|
static builders(options) {
|
|
@@ -5863,7 +6421,7 @@ var Originators = class {
|
|
|
5863
6421
|
...options,
|
|
5864
6422
|
headers: {
|
|
5865
6423
|
"Content-Type": "application/json",
|
|
5866
|
-
...options
|
|
6424
|
+
...options.headers
|
|
5867
6425
|
}
|
|
5868
6426
|
});
|
|
5869
6427
|
}
|
|
@@ -5883,7 +6441,7 @@ var Originators = class {
|
|
|
5883
6441
|
...options,
|
|
5884
6442
|
headers: {
|
|
5885
6443
|
"Content-Type": "application/json",
|
|
5886
|
-
...options
|
|
6444
|
+
...options.headers
|
|
5887
6445
|
}
|
|
5888
6446
|
});
|
|
5889
6447
|
}
|
|
@@ -5903,7 +6461,7 @@ var Originators = class {
|
|
|
5903
6461
|
...options,
|
|
5904
6462
|
headers: {
|
|
5905
6463
|
"Content-Type": "application/json",
|
|
5906
|
-
...options
|
|
6464
|
+
...options.headers
|
|
5907
6465
|
}
|
|
5908
6466
|
});
|
|
5909
6467
|
}
|
|
@@ -5923,7 +6481,7 @@ var Originators = class {
|
|
|
5923
6481
|
...options,
|
|
5924
6482
|
headers: {
|
|
5925
6483
|
"Content-Type": "application/json",
|
|
5926
|
-
...options
|
|
6484
|
+
...options.headers
|
|
5927
6485
|
}
|
|
5928
6486
|
});
|
|
5929
6487
|
}
|
|
@@ -5943,7 +6501,7 @@ var Originators = class {
|
|
|
5943
6501
|
...options,
|
|
5944
6502
|
headers: {
|
|
5945
6503
|
"Content-Type": "application/json",
|
|
5946
|
-
...options
|
|
6504
|
+
...options.headers
|
|
5947
6505
|
}
|
|
5948
6506
|
});
|
|
5949
6507
|
}
|
|
@@ -5963,7 +6521,7 @@ var Originators = class {
|
|
|
5963
6521
|
...options,
|
|
5964
6522
|
headers: {
|
|
5965
6523
|
"Content-Type": "application/json",
|
|
5966
|
-
...options
|
|
6524
|
+
...options.headers
|
|
5967
6525
|
}
|
|
5968
6526
|
});
|
|
5969
6527
|
}
|
|
@@ -5983,12 +6541,13 @@ var Originators = class {
|
|
|
5983
6541
|
...options,
|
|
5984
6542
|
headers: {
|
|
5985
6543
|
"Content-Type": "application/json",
|
|
5986
|
-
...options
|
|
6544
|
+
...options.headers
|
|
5987
6545
|
}
|
|
5988
6546
|
});
|
|
5989
6547
|
}
|
|
5990
6548
|
/**
|
|
5991
6549
|
* Title companies on this LO's loans (spellings merged)
|
|
6550
|
+
*
|
|
5992
6551
|
* Ranks the title companies on this entity's loans (recorded deeds, `recording_date` window — the same population and period axis as every other loans breakdown). Spellings of one company are MERGED: `label` is its most-used spelling, `id` the normalized name every spelling was grouped under (legal-form and filler words such as `inc`, `llc`, `co`, `company`, `title`, `escrow` removed; `natl` → `national`). Placeholder entries meaning "no title company recorded" (`none available` and its misspellings, `unknown`, `n/a`, …) and names shorter than 3 characters are excluded rather than ranked. `attorney` and `accommodation` are kept: they say who closed. `pctUnits` / `pctVolume` are shares of the entity's WHOLE loan population in the window, including loans with no title company, so they do not sum to 100 across the page. Pages of up to 100 via `pagination`.
|
|
5993
6552
|
*/
|
|
5994
6553
|
static titleCompanies(options) {
|
|
@@ -6004,7 +6563,7 @@ var Originators = class {
|
|
|
6004
6563
|
...options,
|
|
6005
6564
|
headers: {
|
|
6006
6565
|
"Content-Type": "application/json",
|
|
6007
|
-
...options
|
|
6566
|
+
...options.headers
|
|
6008
6567
|
}
|
|
6009
6568
|
});
|
|
6010
6569
|
}
|
|
@@ -6024,7 +6583,7 @@ var Originators = class {
|
|
|
6024
6583
|
...options,
|
|
6025
6584
|
headers: {
|
|
6026
6585
|
"Content-Type": "application/json",
|
|
6027
|
-
...options
|
|
6586
|
+
...options.headers
|
|
6028
6587
|
}
|
|
6029
6588
|
});
|
|
6030
6589
|
}
|
|
@@ -6044,12 +6603,13 @@ var Originators = class {
|
|
|
6044
6603
|
...options,
|
|
6045
6604
|
headers: {
|
|
6046
6605
|
"Content-Type": "application/json",
|
|
6047
|
-
...options
|
|
6606
|
+
...options.headers
|
|
6048
6607
|
}
|
|
6049
6608
|
});
|
|
6050
6609
|
}
|
|
6051
6610
|
/**
|
|
6052
6611
|
* The markets this LO lends in
|
|
6612
|
+
*
|
|
6053
6613
|
* One blended view of a loan officer's lending footprint: the ZIP codes they originated in, city / county / state rollups of the same scope, and the period totals those markets are a share of. AVERAGES ARE VOLUME-WEIGHTED: the summary loan size is Σ volume ÷ Σ units, not an unweighted mean of the per-market averages (on a real footprint the two differ by thousands of dollars). Sending `zipCodes` narrows every grain to those ZIPs; sending a `dateRange` re-cuts the window. Either switches the response from the LO's pre-aggregated footprint to a live aggregation of their loans — `source` and `sourceReasons` say which was used, and bucket `key` forms differ between them (use `name` for display). All shares on this response are 0–100 percentages. A summary can cover less than the whole book: production that could not be attributed to a place is held out and reported in `summary.unresolved` rather than being folded in or silently dropped. The summary also carries a Community Lending mix — what kind of neighborhood this book lands in. These are U.S. Census tract-level aggregates describing whole neighborhoods, never individual, household or applicant attributes. Unscoped it is the LO's own whole-period mix; a ZIP or date scope recomputes it over the markets in scope, and `summary.communityLending.basis` says which you got.
|
|
6054
6614
|
*/
|
|
6055
6615
|
static markets(options) {
|
|
@@ -6065,12 +6625,13 @@ var Originators = class {
|
|
|
6065
6625
|
...options,
|
|
6066
6626
|
headers: {
|
|
6067
6627
|
"Content-Type": "application/json",
|
|
6068
|
-
...options
|
|
6628
|
+
...options.headers
|
|
6069
6629
|
}
|
|
6070
6630
|
});
|
|
6071
6631
|
}
|
|
6072
6632
|
/**
|
|
6073
6633
|
* Properties this loan officer has touched
|
|
6634
|
+
*
|
|
6074
6635
|
* Returns the parcels this loan officer is attributed to in public record — the reverse of the `parties` block on `GET /v1/properties/{id}`. Accepts the same filters, sorts and pagination as the main property search, so a caller can ask 'this LO's parcels in Travis County built after 2015' in one request. Attribution is ALL-TIME: a parcel stays in this LO's set after the loan is paid off, because the question is career reach rather than current book. An LO with no attributed parcels returns an empty page, not a 404 — the LO may be real and simply have nothing in the public record yet.
|
|
6075
6636
|
*/
|
|
6076
6637
|
static properties(options) {
|
|
@@ -6086,12 +6647,13 @@ var Originators = class {
|
|
|
6086
6647
|
...options,
|
|
6087
6648
|
headers: {
|
|
6088
6649
|
"Content-Type": "application/json",
|
|
6089
|
-
...options
|
|
6650
|
+
...options.headers
|
|
6090
6651
|
}
|
|
6091
6652
|
});
|
|
6092
6653
|
}
|
|
6093
6654
|
/**
|
|
6094
6655
|
* Borrower retention report for this LO
|
|
6656
|
+
*
|
|
6095
6657
|
* Classifies every loan this LO originated since 2017 against every later loan and MLS sale on the same parcel, for the period `start`–`end`: borrowers kept (the LO refinanced them again), lost (refinanced elsewhere — `churnedLoans`, with who captured them), sold, or a second lien taken elsewhere. Returns the summary, capture lanes (same funding lender vs other companies), capturing companies / LOs (top 25 + full-population totals), timing, monthly trend, the newest 500 loss rows, and exit signals on the retained book (`atRisk`). `compare` adds a second period's `summary` and monthly trend (`previous`) from the same scan. A very large book that cannot be read in time answers `status: "timeout"`.
|
|
6096
6658
|
*/
|
|
6097
6659
|
static retention(options) {
|
|
@@ -6107,7 +6669,7 @@ var Originators = class {
|
|
|
6107
6669
|
...options,
|
|
6108
6670
|
headers: {
|
|
6109
6671
|
"Content-Type": "application/json",
|
|
6110
|
-
...options
|
|
6672
|
+
...options.headers
|
|
6111
6673
|
}
|
|
6112
6674
|
});
|
|
6113
6675
|
}
|
|
@@ -6115,6 +6677,7 @@ var Originators = class {
|
|
|
6115
6677
|
var Properties = class {
|
|
6116
6678
|
/**
|
|
6117
6679
|
* Search properties with filters
|
|
6680
|
+
*
|
|
6118
6681
|
* Search and list individual properties/parcels with filters — one row per parcel. Filter by location (state, county, city, zip, address), owner name, property characteristics (beds, baths, square footage, year built, property type), value, and ownership or transaction history, with sorting and cursor pagination. This is the discrete per-property record search: use it to find specific properties or build a filtered property list. (For a single property by its ID use the property detail endpoint.) If you only need how many properties match and not the records themselves, send the same request body to `countProperties`.
|
|
6119
6682
|
*/
|
|
6120
6683
|
static list(options) {
|
|
@@ -6176,6 +6739,7 @@ var Properties = class {
|
|
|
6176
6739
|
}
|
|
6177
6740
|
/**
|
|
6178
6741
|
* Submit a bulk-delivery job for properties
|
|
6742
|
+
*
|
|
6179
6743
|
* Queues an ECS task that dumps every matching properties document to S3 in the requested format. Returns 202 with a jobId; poll `GET /v1/properties/bulk-delivery/{jobId}` for status + the signed download URL.
|
|
6180
6744
|
*
|
|
6181
6745
|
* **Row limit.** Deliveries of up to 5,000 rows need no entitlement. Above that, the org's `bulk-delivery.properties` entitlement is required and its scope (row ceiling, row filters, allowed fields) governs the delivery; without it the request is rejected with 403 `entitlement_missing`. Pass `limit` at or below the ceiling to deliver a capped subset of a broader query. Email support@modelmatch.com to request a limit increase.
|
|
@@ -6203,6 +6767,7 @@ var Properties = class {
|
|
|
6203
6767
|
}
|
|
6204
6768
|
/**
|
|
6205
6769
|
* Cancel a bulk-delivery job for properties
|
|
6770
|
+
*
|
|
6206
6771
|
* Cancels a queued or running properties delivery job.
|
|
6207
6772
|
*
|
|
6208
6773
|
* The job is marked `cancelled` immediately; the container running it notices on its next page boundary and stops. Because a delivery is billed once, at the end, **a cancelled job is never charged** — no credits are debited and there is nothing to refund. No partial file is written.
|
|
@@ -6240,6 +6805,7 @@ var Properties = class {
|
|
|
6240
6805
|
}
|
|
6241
6806
|
/**
|
|
6242
6807
|
* Count properties matching filters
|
|
6808
|
+
*
|
|
6243
6809
|
* Return the exact number of properties matching the given filters. Accepts the same request body as `listProperties` (pagination and sort are ignored). Use this when you only need a total; to get the matching properties themselves, send the same request body to `listProperties`.
|
|
6244
6810
|
*/
|
|
6245
6811
|
static count(options) {
|
|
@@ -6261,6 +6827,7 @@ var Properties = class {
|
|
|
6261
6827
|
}
|
|
6262
6828
|
/**
|
|
6263
6829
|
* Enrich several properties with owner contact info in one request
|
|
6830
|
+
*
|
|
6264
6831
|
* Looks up owner contact information for up to 50 properties in a single synchronous request. Each id is resolved independently and returned in the `results` array with its own status — a bad id never fails the batch. Each match debits 10 credits; cache hits and no-matches are free. Every ok item also carries `property` — the parcel's Community Lending neighborhood profile and mortgage party rosters. For larger sets use the asynchronous bulk job.
|
|
6265
6832
|
*/
|
|
6266
6833
|
static enrichPropertiesBatch(options) {
|
|
@@ -6282,6 +6849,7 @@ var Properties = class {
|
|
|
6282
6849
|
}
|
|
6283
6850
|
/**
|
|
6284
6851
|
* Submit a bulk skip-trace job
|
|
6852
|
+
*
|
|
6285
6853
|
* Queues an ECS task that enriches up to 50000 properties. Returns 202 with a jobId; poll `GET /v1/properties/enrich-bulk/{jobId}` or subscribe to the `enrichment.bulk.*` EventBridge / webhook events for completion.
|
|
6286
6854
|
*/
|
|
6287
6855
|
static enrichPropertiesBulk(options) {
|
|
@@ -6303,6 +6871,7 @@ var Properties = class {
|
|
|
6303
6871
|
}
|
|
6304
6872
|
/**
|
|
6305
6873
|
* Cancel a bulk enrichment job
|
|
6874
|
+
*
|
|
6306
6875
|
* Cancels a queued or running bulk enrichment job.
|
|
6307
6876
|
*
|
|
6308
6877
|
* The job is marked `cancelled` immediately; the container running it notices at its next progress tick and stops. Enrichment is billed once, at the end, so **a cancelled job is never charged** — no credits are debited and there is nothing to refund. Properties already enriched stay in the cache, so re-running later is cheaper.
|
|
@@ -6356,6 +6925,7 @@ var Properties = class {
|
|
|
6356
6925
|
}
|
|
6357
6926
|
/**
|
|
6358
6927
|
* Resolve a batch of addresses to property ids
|
|
6928
|
+
*
|
|
6359
6929
|
* Resolve up to 2,000 postal addresses to property ids in one call — e.g. a mailing list before a bulk delivery. Free. Returns one result per input, in order, keyed by your `ref`. `matched` carries the parcel `id` and `mmPropertyId` — pass them to bulk delivery `propertyIds` or the list `flatFilters.id`, then join the rows back on `ref`. Each address is first matched on the normalized number + street + unit + zip key (suffix, directional, punctuation and case insensitive); misses fall back to a ranked search that only accepts a hit with the same house number, the same zip or city, and a near-identical street name. `ambiguous` lists `candidates`: `unit_required` (a building whose units are separate parcels — resend with the unit), `duplicate_parcels` (one address on several parcel records; usually safe to take them all), `multiple_parcels`. `not_found` gives a `reason`: `no_parcel_at_number` (no parcel at that house number in that zip/city), `low_confidence`, or an input problem (`no_house_number`, `no_street`, `no_location`).
|
|
6360
6930
|
*/
|
|
6361
6931
|
static resolve(options) {
|
|
@@ -6377,6 +6947,7 @@ var Properties = class {
|
|
|
6377
6947
|
}
|
|
6378
6948
|
/**
|
|
6379
6949
|
* Free-text property search
|
|
6950
|
+
*
|
|
6380
6951
|
* Find properties by a single free-text query — a full or partial address, an owner name, or a place. Results are ranked by relevance and tolerate typos, missing components, and reordered street directionals (e.g. "112 5th ave nw" and "112 nw 5th ave" both match). Returns the same property summary rows as the list endpoint. Use this for a search box; use the list endpoint for structured filtering.
|
|
6381
6952
|
*/
|
|
6382
6953
|
static search(options) {
|
|
@@ -6414,6 +6985,7 @@ var Properties = class {
|
|
|
6414
6985
|
}
|
|
6415
6986
|
/**
|
|
6416
6987
|
* Enrich a property with owner contact info
|
|
6988
|
+
*
|
|
6417
6989
|
* Looks up owner contact information via skip-trace. Uses the canonical address first; falls back to an associated loan or sale record address if the canonical is missing. The response also carries `property` — the parcel's Community Lending neighborhood profile and its mortgage party rosters, the same blocks `GET /v1/properties/{id}` returns — so the two questions that follow a skip-trace do not need a second call. `property` is `null` when the id resolves to more than one parcel and the request was served from cache (a fresh lookup 409s instead, rather than bill for a guess).
|
|
6418
6990
|
*/
|
|
6419
6991
|
static enrich(options) {
|
|
@@ -6433,6 +7005,7 @@ var Properties = class {
|
|
|
6433
7005
|
var Realtime = class {
|
|
6434
7006
|
/**
|
|
6435
7007
|
* Get realtime connection config
|
|
7008
|
+
*
|
|
6436
7009
|
* Returns the realtime/notifications connection info (endpoint, authorizer, app, stage) merged with the caller's userId, so a trusted client can connect to its per-user IoT MQTT topic.
|
|
6437
7010
|
*/
|
|
6438
7011
|
static getRealtimeConfig(options) {
|
|
@@ -6452,6 +7025,7 @@ var Realtime = class {
|
|
|
6452
7025
|
var Sales = class {
|
|
6453
7026
|
/**
|
|
6454
7027
|
* Search sales with filters
|
|
7028
|
+
*
|
|
6455
7029
|
* Search and list individual real-estate sale transactions and active listings with filters — one row per sale/listing. Filter by location (state, county, city, zip), sale price, sale or listing date, property characteristics (beds, baths, square footage, property type), and listing status, with sorting and cursor pagination. This is the discrete per-transaction sales-record search: use it to find specific sales or build a filtered list of sold/active listings. If you only need how many sales match and not the records themselves, send the same request body to `countSales`.
|
|
6456
7030
|
*/
|
|
6457
7031
|
static list(options) {
|
|
@@ -6533,6 +7107,7 @@ var Sales = class {
|
|
|
6533
7107
|
}
|
|
6534
7108
|
/**
|
|
6535
7109
|
* Count sales matching filters
|
|
7110
|
+
*
|
|
6536
7111
|
* Return the exact number of sales matching the given filters. Accepts the same request body as `listSales` (pagination and sort are ignored). Use this when you only need a total; to get the matching sales themselves, send the same request body to `listSales`.
|
|
6537
7112
|
*/
|
|
6538
7113
|
static count(options) {
|
|
@@ -6572,6 +7147,7 @@ var Sales = class {
|
|
|
6572
7147
|
var SavedFilters = class {
|
|
6573
7148
|
/**
|
|
6574
7149
|
* List your saved filters
|
|
7150
|
+
*
|
|
6575
7151
|
* The caller's saved filters (and saved CRM views) in the active organization, oldest first, optionally narrowed by target and kind.
|
|
6576
7152
|
*/
|
|
6577
7153
|
static listSavedFilters(options) {
|
|
@@ -6589,6 +7165,7 @@ var SavedFilters = class {
|
|
|
6589
7165
|
}
|
|
6590
7166
|
/**
|
|
6591
7167
|
* Save a filter
|
|
7168
|
+
*
|
|
6592
7169
|
* Save a named filter for a list target. For a market target, `query` is the target operation's request body without `pagination` (e.g. the body you would send to listOriginators) and is validated against it. Limit: 25 per target.
|
|
6593
7170
|
*/
|
|
6594
7171
|
static createSavedFilter(options) {
|
|
@@ -6626,6 +7203,7 @@ var SavedFilters = class {
|
|
|
6626
7203
|
}
|
|
6627
7204
|
/**
|
|
6628
7205
|
* Get a saved filter (with the operation to run it)
|
|
7206
|
+
*
|
|
6629
7207
|
* Returns the saved `query` and the `operationId` to run it with. Check `fidelity` (`partial` → `unmapped` lists what the query omits; `ui_only` → nothing to run) and `stale` (the query no longer validates) before running.
|
|
6630
7208
|
*/
|
|
6631
7209
|
static getSavedFilter(options) {
|
|
@@ -6643,6 +7221,7 @@ var SavedFilters = class {
|
|
|
6643
7221
|
}
|
|
6644
7222
|
/**
|
|
6645
7223
|
* Update a saved filter
|
|
7224
|
+
*
|
|
6646
7225
|
* Rename, re-icon, or replace the query / UI state. The target is fixed. A new `query` is validated like on create.
|
|
6647
7226
|
*/
|
|
6648
7227
|
static updateSavedFilter(options) {
|
|
@@ -6658,7 +7237,7 @@ var SavedFilters = class {
|
|
|
6658
7237
|
...options,
|
|
6659
7238
|
headers: {
|
|
6660
7239
|
"Content-Type": "application/json",
|
|
6661
|
-
...options
|
|
7240
|
+
...options.headers
|
|
6662
7241
|
}
|
|
6663
7242
|
});
|
|
6664
7243
|
}
|
|
@@ -6666,12 +7245,24 @@ var SavedFilters = class {
|
|
|
6666
7245
|
//#endregion
|
|
6667
7246
|
//#region src/index.ts
|
|
6668
7247
|
/**
|
|
7248
|
+
* Builds a standalone client for multi-tenant callers (per-user auth,
|
|
7249
|
+
* per-call client) — pass it as a generated method's `options.client` to
|
|
7250
|
+
* scope auth to that request. Same `baseUrl` default as the shared client;
|
|
7251
|
+
* everything else is the generated fetch client's own defaults.
|
|
7252
|
+
*/
|
|
7253
|
+
function createApiClient(config = {}) {
|
|
7254
|
+
return createClient$1({
|
|
7255
|
+
...config,
|
|
7256
|
+
baseUrl: config.baseUrl ?? defaultBaseUrl()
|
|
7257
|
+
});
|
|
7258
|
+
}
|
|
7259
|
+
/**
|
|
6669
7260
|
* Configures the singleton hey-api fetch client and returns a namespace-grouped
|
|
6670
7261
|
* facade. The static service classes share the global client, so a process
|
|
6671
7262
|
* should call `createClient()` once at startup. For multi-tenant scenarios,
|
|
6672
7263
|
* pass a custom `client` per call via the per-method `Options.client` field.
|
|
6673
7264
|
*/
|
|
6674
|
-
function createClient
|
|
7265
|
+
function createClient(config = {}) {
|
|
6675
7266
|
if (config.baseUrl || config.headers || config.token) client.setConfig({
|
|
6676
7267
|
...config.baseUrl ? { baseUrl: config.baseUrl } : {},
|
|
6677
7268
|
...config.headers ? { headers: config.headers } : {},
|
|
@@ -6701,4 +7292,4 @@ function createClient$1(config = {}) {
|
|
|
6701
7292
|
};
|
|
6702
7293
|
}
|
|
6703
7294
|
//#endregion
|
|
6704
|
-
export {
|
|
7295
|
+
export { client as S, Realtime as _, Branches as a, SavedFilters as b, Integrations as c, Locations as d, Market as f, Properties as g, Originators as h, Alerts as i, Lenders as l, Offices as m, createClient as n, Companies as o, Me as p, Agents as r, Crm as s, createApiClient as t, Loans as u, Related as v, Search as x, Sales as y };
|