-
Notifications
You must be signed in to change notification settings - Fork 3.7k
Expand file tree
/
Copy pathroute.ts
More file actions
98 lines (84 loc) · 3.3 KB
/
Copy pathroute.ts
File metadata and controls
98 lines (84 loc) · 3.3 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
import { createLogger } from '@sim/logger'
import { getErrorMessage, toError } from '@sim/utils/errors'
import { type NextRequest, NextResponse } from 'next/server'
import { jsmObjectTypeAttributesContract } from '@/lib/api/contracts/selectors/jsm'
import { parseRequest } from '@/lib/api/server'
import { checkInternalAuth } from '@/lib/auth/hybrid'
import {
validateAssetsWorkspaceId,
validateJiraCloudId,
} from '@/lib/core/security/input-validation'
import { withRouteHandler } from '@/lib/core/utils/with-route-handler'
import { parseAtlassianErrorMessage } from '@/tools/jira/utils'
import { getAssetsApiBaseUrl, getJsmHeaders, resolveAssetsContext } from '@/tools/jsm/utils'
export const dynamic = 'force-dynamic'
const logger = createLogger('JsmAssetsAttributesAPI')
export const POST = withRouteHandler(async (request: NextRequest) => {
const auth = await checkInternalAuth(request)
if (!auth.success || !auth.userId) {
return NextResponse.json({ error: auth.error || 'Unauthorized' }, { status: 401 })
}
try {
const parsed = await parseRequest(jsmObjectTypeAttributesContract, request, {})
if (!parsed.success) return parsed.response
const {
domain,
accessToken,
cloudId: cloudIdParam,
workspaceId: workspaceIdParam,
objectTypeId,
onlyValueEditable,
query: searchQuery,
} = parsed.data.body
const { cloudId, workspaceId } = await resolveAssetsContext(
domain,
accessToken,
cloudIdParam,
workspaceIdParam
)
const cloudIdValidation = validateJiraCloudId(cloudId, 'cloudId')
if (!cloudIdValidation.isValid) {
return NextResponse.json({ error: cloudIdValidation.error }, { status: 400 })
}
const workspaceIdValidation = validateAssetsWorkspaceId(workspaceId, 'workspaceId')
if (!workspaceIdValidation.isValid) {
return NextResponse.json({ error: workspaceIdValidation.error }, { status: 400 })
}
const query = new URLSearchParams()
if (onlyValueEditable !== undefined) {
query.append('onlyValueEditable', String(onlyValueEditable))
}
if (searchQuery) query.append('query', searchQuery)
const url = `${getAssetsApiBaseUrl(cloudId, workspaceId)}/objecttype/${encodeURIComponent(
objectTypeId
)}/attributes${query.toString() ? `?${query.toString()}` : ''}`
const response = await fetch(url, { method: 'GET', headers: getJsmHeaders(accessToken) })
if (!response.ok) {
const errorText = await response.text()
logger.error('Assets API error getting attributes', { status: response.status, errorText })
return NextResponse.json(
{
error: parseAtlassianErrorMessage(response.status, response.statusText, errorText),
details: errorText,
},
{ status: response.status }
)
}
const data = await response.json()
const attributes = Array.isArray(data) ? data : (data.values ?? [])
return NextResponse.json({
success: true,
output: {
ts: new Date().toISOString(),
attributes,
total: attributes.length,
},
})
} catch (error) {
logger.error('Error getting Assets attributes', { error: toError(error).message })
return NextResponse.json(
{ error: getErrorMessage(error, 'Internal server error'), success: false },
{ status: 500 }
)
}
})