1
1
/** @jsxImportSource @emotion /react */
2
+ import { useState } from "react" ;
2
3
import { css } from "@emotion/react" ;
3
4
import { token } from "@atlaskit/tokens" ;
4
5
import analyticsClient from "../../../analytics" ;
5
6
import { popup } from "../../../utils" ;
7
+ import { CheckAdminOrgSource , DeferredInstallationUrlParams } from "rest-interfaces" ;
8
+ import { HostUrlType } from "../../../utils/modifyError" ;
9
+ import Api from "../../../api" ;
10
+ import Modal , {
11
+ ModalBody ,
12
+ ModalFooter ,
13
+ ModalHeader ,
14
+ ModalTitle ,
15
+ ModalTransition ,
16
+ } from "@atlaskit/modal-dialog" ;
17
+ import TextArea from "@atlaskit/textarea" ;
18
+ import Spinner from "@atlaskit/spinner" ;
19
+ import Button from "@atlaskit/button" ;
6
20
21
+ const olStyle = css `
22
+ padding-left : 1.2em ;
23
+ ` ;
7
24
const paragraphStyle = css `
8
25
color : ${ token ( "color.text.subtle" ) } ;
9
26
` ;
@@ -15,6 +32,9 @@ const linkStyle = css`
15
32
padding-left : 0 ;
16
33
padding-right : 0 ;
17
34
` ;
35
+ const textAreaStyle = css `
36
+ margin-top : 20px ;
37
+ ` ;
18
38
19
39
/************************************************************************
20
40
* UI view for the 3 known errors
@@ -39,14 +59,108 @@ export const ErrorForSSO = ({ orgName, accessUrl, resetCallback, onPopupBlocked
39
59
</ div >
40
60
</ > ;
41
61
42
- export const ErrorForNonAdmins = ( { orgName, adminOrgsUrl } : { orgName ?: string ; adminOrgsUrl : string ; } ) => < div css = { paragraphStyle } >
43
- Can't connect, you're not the organization owner{ orgName && < span > of < b > { orgName } </ b > </ span > } .< br />
44
- Ask an < a css = { linkStyle } onClick = { ( ) => {
45
- // TODO: Need to get this URL for Enterprise users too, this is only for Cloud users
46
- popup ( adminOrgsUrl ) ;
47
- analyticsClient . sendUIEvent ( { actionSubject : "checkOrgAdmin" , action : "clicked" } , { type : "cloud" } ) ;
48
- } } > organization owner</ a > to complete this step.
49
- </ div > ;
62
+ export const ErrorForNonAdmins = ( { orgName, adminOrgsUrl, onPopupBlocked, deferredInstallationOrgDetails , hostUrl} : {
63
+ orgName ?: string ;
64
+ adminOrgsUrl : string ;
65
+ onPopupBlocked : ( ) => void ;
66
+ deferredInstallationOrgDetails : DeferredInstallationUrlParams ;
67
+ hostUrl ?: HostUrlType ;
68
+ } ) => {
69
+ const [ isOpen , setIsOpen ] = useState < boolean > ( false ) ;
70
+ const [ isLoading , setIsLoading ] = useState < boolean > ( false ) ;
71
+ const [ deferredInstallationUrl , setDeferredInstallationUrl ] = useState < string | null > ( null ) ;
72
+
73
+ const getOrgOwnerUrl = async ( from : CheckAdminOrgSource ) => {
74
+ // TODO: Need to get this URL for Enterprise users too, this is only for Cloud users
75
+ const win = popup ( adminOrgsUrl ) ;
76
+ if ( win === null ) onPopupBlocked ( ) ;
77
+ analyticsClient . sendUIEvent ( { actionSubject : "checkOrgAdmin" , action : "clicked" } , { type : "cloud" , from } ) ;
78
+ } ;
79
+
80
+ const getDeferredInstallationUrl = async ( ) => {
81
+ if ( ! isOpen ) {
82
+ analyticsClient . sendScreenEvent ( { name : "DeferredInstallationModal" } , { type : "cloud" } ) ;
83
+ try {
84
+ setIsOpen ( true ) ;
85
+ setIsLoading ( true ) ;
86
+ const response = await Api . deferral . getDeferredInstallationUrl ( {
87
+ gitHubInstallationId : deferredInstallationOrgDetails ?. gitHubInstallationId ,
88
+ gitHubOrgName : deferredInstallationOrgDetails ?. gitHubOrgName
89
+ } ) ;
90
+ setDeferredInstallationUrl ( response . data . deferredInstallUrl ) ;
91
+ analyticsClient . sendUIEvent ( { actionSubject : "generateDeferredInstallationLink" , action : "clicked" } , { type : "cloud" } ) ;
92
+ } catch ( e ) {
93
+ // TODO: handle this error in UI/Modal ?
94
+ console . error ( "Could not fetch the deferred installation url: " , e ) ;
95
+ } finally {
96
+ setIsLoading ( false ) ;
97
+ }
98
+ }
99
+ } ;
100
+
101
+ const closeModal = ( ) => {
102
+ setIsOpen ( false ) ;
103
+ setDeferredInstallationUrl ( null ) ;
104
+ analyticsClient . sendUIEvent ( { actionSubject : "closedDeferredInstallationModal" , action : "clicked" } , { type : "cloud" } ) ;
105
+ } ;
106
+ return (
107
+ < div css = { paragraphStyle } >
108
+ You’re not an owner for this organization. To connect:
109
+ < ol css = { olStyle } >
110
+ < li >
111
+ < a css = { linkStyle } onClick = { ( ) => getOrgOwnerUrl ( "ErrorInOrgList" ) } >
112
+ Find an organization owner.
113
+ </ a >
114
+ </ li >
115
+ < li >
116
+ < a css = { linkStyle } onClick = { getDeferredInstallationUrl } >
117
+ Send them a link and ask them to connect.
118
+ </ a >
119
+ </ li >
120
+ </ ol >
121
+ < ModalTransition >
122
+ { isOpen && (
123
+ < Modal onClose = { closeModal } >
124
+ { isLoading ? (
125
+ < Spinner interactionName = "load" />
126
+ ) : (
127
+ < >
128
+ < ModalHeader >
129
+ < ModalTitle > Send a link to an organization owner</ ModalTitle >
130
+ </ ModalHeader >
131
+ < ModalBody >
132
+ < div css = { paragraphStyle } >
133
+ Copy the message and URL below, and send it to an
134
+ organization owner to approve.
135
+ < br />
136
+ < a css = { linkStyle } onClick = { ( ) => getOrgOwnerUrl ( "DeferredInstallationModal" ) } >
137
+ Find an organization owner
138
+ </ a >
139
+ </ div >
140
+ < TextArea
141
+ onCopy = { ( ) => {
142
+ analyticsClient . sendUIEvent ( { actionSubject : "copiedDeferredInstallationUrl" , action : "clicked" } , { type : "cloud" } ) ;
143
+ } }
144
+ css = { textAreaStyle }
145
+ id = "deffered-installation-msg"
146
+ name = "deffered-installation-msg"
147
+ defaultValue = { `I want to connect the GitHub organization ${ orgName } to the Jira site ${ hostUrl ?. jiraHost } , and I need your approval as an organization owner.\n\nIf you approve, can you go to this link and complete the connection?\n\n${ deferredInstallationUrl } ` }
148
+ readOnly
149
+ />
150
+ </ ModalBody >
151
+ < ModalFooter >
152
+ < Button appearance = "primary" onClick = { closeModal } autoFocus >
153
+ Close
154
+ </ Button >
155
+ </ ModalFooter >
156
+ </ >
157
+ ) }
158
+ </ Modal >
159
+ ) }
160
+ </ ModalTransition >
161
+ </ div >
162
+ ) ;
163
+ } ;
50
164
51
165
export const ErrorForPopupBlocked = ( { onDismiss } : { onDismiss : ( ) => void } ) => (
52
166
< >
0 commit comments