feat: port bulk editor textareas to codemirror

This commit is contained in:
liyasthomas
2021-09-08 21:52:26 +05:30
parent e1a25fa894
commit b15fd6c75a
4 changed files with 303 additions and 404 deletions

View File

@@ -36,7 +36,8 @@
}
input::placeholder,
textarea::placeholder {
textarea::placeholder,
.CodeMirror-empty {
@apply text-secondaryDark;
@apply opacity-25;
}

View File

@@ -42,9 +42,7 @@
/>
<ButtonSecondary
v-tippy="{ theme: 'tooltip' }"
:title="`${$t(
'action.prettify'
)} <kbd>${getSpecialKey()}</kbd><kbd>P</kbd>`"
:title="$t('action.prettify')"
:svg="prettifyQueryIcon"
@click.native="prettifyQuery"
/>
@@ -174,25 +172,7 @@
</div>
</div>
<div v-if="bulkMode" class="flex">
<textarea-autosize
v-model="bulkHeaders"
v-focus
name="bulk-parameters"
class="
bg-transparent
border-b border-dividerLight
flex
font-mono
flex-1
py-2
px-4
whitespace-pre
resize-y
overflow-auto
"
rows="10"
:placeholder="$t('state.bulk_mode_placeholder')"
/>
<div ref="bulkEditor" class="w-full block"></div>
</div>
<div v-else>
<div
@@ -229,7 +209,9 @@
/>
<input
class="bg-transparent flex flex-1 py-2 px-4"
:placeholder="$t('count.value', { count: index + 1 })"
:placeholder="
$t('count.value', { count: index + 1 }).toString()
"
:name="`value ${index}`"
:value="header.value"
autofocus
@@ -311,17 +293,9 @@
</div>
</template>
<script lang="ts">
import {
defineComponent,
onMounted,
PropType,
ref,
useContext,
watch,
} from "@nuxtjs/composition-api"
<script setup lang="ts">
import { onMounted, ref, useContext, watch } from "@nuxtjs/composition-api"
import clone from "lodash/clone"
import { getPlatformSpecialKey } from "~/helpers/platformutils"
import { copyToClipboard } from "~/helpers/utils/clipboard"
import {
useNuxt,
@@ -348,26 +322,23 @@ import { makeGQLHistoryEntry, addGraphqlHistoryEntry } from "~/newstore/history"
import { logHoppRequestRunToAnalytics } from "~/helpers/fb/analytics"
import { getCurrentStrategyID } from "~/helpers/network"
import { makeGQLRequest } from "~/helpers/types/HoppGQLRequest"
import { useCodemirror } from "~/helpers/editor/codemirror"
export default defineComponent({
props: {
conn: {
type: Object as PropType<GQLConnection>,
required: true,
},
},
setup(props) {
const {
const props = defineProps<{
conn: GQLConnection
}>()
const {
$toast,
app: { i18n },
} = useContext()
const t = i18n.t.bind(i18n)
const nuxt = useNuxt()
} = useContext()
const t = i18n.t.bind(i18n)
const nuxt = useNuxt()
const bulkMode = ref(false)
const bulkHeaders = ref("")
const bulkMode = ref(false)
const bulkHeaders = ref("")
watch(bulkHeaders, () => {
watch(bulkHeaders, () => {
try {
const transformation = bulkHeaders.value.split("\n").map((item) => ({
key: item.substring(0, item.indexOf(":")).trim().replace(/^\/\//, ""),
@@ -381,24 +352,33 @@ export default defineComponent({
})
console.error(e)
}
})
})
const url = useReadonlyStream(gqlURL$, "")
const gqlQueryString = useStream(gqlQuery$, "", setGQLQuery)
const variableString = useStream(gqlVariables$, "", setGQLVariables)
const headers = useStream(gqlHeaders$, [], setGQLHeaders)
const url = useReadonlyStream(gqlURL$, "")
const gqlQueryString = useStream(gqlQuery$, "", setGQLQuery)
const variableString = useStream(gqlVariables$, "", setGQLVariables)
const headers = useStream(gqlHeaders$, [], setGQLHeaders)
const queryEditor = ref<any | null>(null)
const bulkEditor = ref<any | null>(null)
const copyQueryIcon = ref("copy")
const prettifyQueryIcon = ref("align-left")
const copyVariablesIcon = ref("copy")
useCodemirror(bulkEditor, bulkHeaders, {
extendedEditorConfig: {
mode: "text/x-yaml",
placeholder: t("state.bulk_mode_placeholder").toString(),
},
linter: null,
completer: null,
})
const showSaveRequestModal = ref(false)
const queryEditor = ref<any | null>(null)
const schema = useReadonlyStream(props.conn.schemaString$, "")
const copyQueryIcon = ref("copy")
const prettifyQueryIcon = ref("align-left")
const copyVariablesIcon = ref("copy")
watch(
const showSaveRequestModal = ref(false)
watch(
headers,
() => {
if (
@@ -409,23 +389,23 @@ export default defineComponent({
addRequestHeader()
},
{ deep: true }
)
)
onMounted(() => {
onMounted(() => {
if (!headers.value?.length) {
addRequestHeader()
}
})
})
const copyQuery = () => {
const copyQuery = () => {
copyToClipboard(gqlQueryString.value)
copyQueryIcon.value = "check"
setTimeout(() => (copyQueryIcon.value = "copy"), 1000)
}
}
const response = useStream(gqlResponse$, "", setGQLResponse)
const response = useStream(gqlResponse$, "", setGQLResponse)
const runQuery = async () => {
const runQuery = async () => {
const startTime = Date.now()
nuxt.value.$loading.start()
@@ -480,76 +460,42 @@ export default defineComponent({
platform: "graphql-query",
strategy: getCurrentStrategyID(),
})
}
}
const hideRequestModal = () => {
const hideRequestModal = () => {
showSaveRequestModal.value = false
}
}
const prettifyQuery = () => {
const prettifyQuery = () => {
queryEditor.value.prettifyQuery()
prettifyQueryIcon.value = "check"
setTimeout(() => (prettifyQueryIcon.value = "align-left"), 1000)
}
}
const saveRequest = () => {
const saveRequest = () => {
showSaveRequestModal.value = true
}
}
// Why ?
const updateQuery = (updatedQuery: string) => {
// Why ?
const updateQuery = (updatedQuery: string) => {
gqlQueryString.value = updatedQuery
}
}
const copyVariables = () => {
const copyVariables = () => {
copyToClipboard(variableString.value)
copyVariablesIcon.value = "check"
setTimeout(() => (copyVariablesIcon.value = "copy"), 1000)
}
}
const addRequestHeader = () => {
const addRequestHeader = () => {
addGQLHeader({
key: "",
value: "",
active: true,
})
}
}
const removeRequestHeader = (index: number) => {
const removeRequestHeader = (index: number) => {
removeGQLHeader(index)
}
return {
gqlQueryString,
variableString,
headers,
copyQueryIcon,
prettifyQueryIcon,
copyVariablesIcon,
queryEditor,
showSaveRequestModal,
hideRequestModal,
schema,
copyQuery,
runQuery,
prettifyQuery,
saveRequest,
updateQuery,
copyVariables,
addRequestHeader,
removeRequestHeader,
getSpecialKey: getPlatformSpecialKey,
commonHeaders,
updateGQLHeader,
bulkMode,
bulkHeaders,
}
},
})
}
</script>

View File

@@ -48,25 +48,7 @@
</div>
</div>
<div v-if="bulkMode" class="flex">
<textarea-autosize
v-model="bulkHeaders"
v-focus
name="bulk-headers"
class="
bg-transparent
border-b border-dividerLight
flex
font-mono
flex-1
py-2
px-4
whitespace-pre
resize-y
overflow-auto
"
rows="10"
:placeholder="$t('state.bulk_mode_placeholder')"
/>
<div ref="bulkEditor" class="w-full block"></div>
</div>
<div v-else>
<div
@@ -193,38 +175,42 @@
</AppSection>
</template>
<script lang="ts">
<script setup lang="ts">
import { ref, useContext, watch } from "@nuxtjs/composition-api"
import { useCodemirror } from "~/helpers/editor/codemirror"
import {
defineComponent,
ref,
useContext,
watch,
} from "@nuxtjs/composition-api"
import {
restHeaders$,
addRESTHeader,
updateRESTHeader,
deleteRESTHeader,
deleteAllRESTHeaders,
deleteRESTHeader,
restHeaders$,
setRESTHeaders,
updateRESTHeader,
} from "~/newstore/RESTSession"
import { commonHeaders } from "~/helpers/headers"
import { useSetting } from "~/newstore/settings"
import { useReadonlyStream } from "~/helpers/utils/composables"
import { HoppRESTHeader } from "~/helpers/types/HoppRESTRequest"
export default defineComponent({
setup() {
const {
const {
$toast,
app: { i18n },
} = useContext()
const t = i18n.t.bind(i18n)
} = useContext()
const t = i18n.t.bind(i18n)
const bulkMode = ref(false)
const bulkHeaders = ref("")
const bulkMode = ref(false)
const bulkHeaders = ref("")
const bulkEditor = ref<any | null>(null)
watch(bulkHeaders, () => {
useCodemirror(bulkEditor, bulkHeaders, {
extendedEditorConfig: {
mode: "text/x-yaml",
placeholder: t("state.bulk_mode_placeholder").toString(),
},
linter: null,
completer: null,
})
watch(bulkHeaders, () => {
try {
const transformation = bulkHeaders.value.split("\n").map((item) => ({
key: item.substring(0, item.indexOf(":")).trim().replace(/^\/\//, ""),
@@ -238,51 +224,37 @@ export default defineComponent({
})
console.error(e)
}
})
})
return {
headers$: useReadonlyStream(restHeaders$, []),
EXPERIMENTAL_URL_BAR_ENABLED: useSetting("EXPERIMENTAL_URL_BAR_ENABLED"),
bulkMode,
bulkHeaders,
}
},
data() {
return {
commonHeaders,
}
},
watch: {
headers$: {
handler(newValue) {
const headers$ = useReadonlyStream(restHeaders$, [])
watch(
headers$,
(newValue) => {
if (
(newValue[newValue.length - 1]?.key !== "" ||
newValue[newValue.length - 1]?.value !== "") &&
newValue.length
)
this.addHeader()
addHeader()
},
deep: true,
},
},
// mounted() {
// if (!this.headers$?.length) {
// this.addHeader()
// }
// },
methods: {
addHeader() {
{ deep: true }
)
const addHeader = () => {
addRESTHeader({ key: "", value: "", active: true })
},
updateHeader(index: number, item: HoppRESTHeader) {
}
const updateHeader = (index: number, item: HoppRESTHeader) => {
updateRESTHeader(index, item)
},
deleteHeader(index: number) {
}
const deleteHeader = (index: number) => {
deleteRESTHeader(index)
},
clearContent() {
}
const clearContent = () => {
deleteAllRESTHeaders()
},
},
})
}
const EXPERIMENTAL_URL_BAR_ENABLED = useSetting("EXPERIMENTAL_URL_BAR_ENABLED")
</script>

View File

@@ -48,25 +48,7 @@
</div>
</div>
<div v-if="bulkMode" class="flex">
<textarea-autosize
v-model="bulkParams"
v-focus
name="bulk-parameters"
class="
bg-transparent
border-b border-dividerLight
flex
font-mono font-medium
flex-1
py-2
px-4
whitespace-pre
resize-y
overflow-auto
"
rows="10"
:placeholder="$t('state.bulk_mode_placeholder')"
/>
<div ref="bulkEditor" class="w-full block"></div>
</div>
<div v-else>
<div
@@ -96,7 +78,7 @@
<input
v-else
class="bg-transparent flex flex-1 py-2 px-4"
:placeholder="$t('count.parameter', { count: index + 1 })"
:placeholder="$t('count.parameter', { count: index + 1 }).toString()"
:name="'param' + index"
:value="param.key"
autofocus
@@ -130,7 +112,7 @@
<input
v-else
class="bg-transparent flex flex-1 py-2 px-4"
:placeholder="$t('count.value', { count: index + 1 })"
:placeholder="$t('count.value', { count: index + 1 }).toString()"
:name="'value' + index"
:value="param.value"
@change="
@@ -202,13 +184,9 @@
</AppSection>
</template>
<script lang="ts">
import {
defineComponent,
ref,
useContext,
watch,
} from "@nuxtjs/composition-api"
<script setup lang="ts">
import { ref, useContext, watch } from "@nuxtjs/composition-api"
import { useCodemirror } from "~/helpers/editor/codemirror"
import { HoppRESTParam } from "~/helpers/types/HoppRESTRequest"
import { useReadonlyStream } from "~/helpers/utils/composables"
import {
@@ -220,19 +198,18 @@ import {
setRESTParams,
} from "~/newstore/RESTSession"
import { useSetting } from "~/newstore/settings"
import "codemirror/mode/yaml/yaml"
export default defineComponent({
setup() {
const {
const {
$toast,
app: { i18n },
} = useContext()
const t = i18n.t.bind(i18n)
} = useContext()
const t = i18n.t.bind(i18n)
const bulkMode = ref(false)
const bulkParams = ref("")
const bulkMode = ref(false)
const bulkParams = ref("")
watch(bulkParams, () => {
watch(bulkParams, () => {
try {
const transformation = bulkParams.value.split("\n").map((item) => ({
key: item.substring(0, item.indexOf(":")).trim().replace(/^\/\//, ""),
@@ -246,46 +223,49 @@ export default defineComponent({
})
console.error(e)
}
})
})
return {
params$: useReadonlyStream(restParams$, []),
EXPERIMENTAL_URL_BAR_ENABLED: useSetting("EXPERIMENTAL_URL_BAR_ENABLED"),
bulkMode,
bulkParams,
}
const bulkEditor = ref<any | null>(null)
useCodemirror(bulkEditor, bulkParams, {
extendedEditorConfig: {
mode: "text/x-yaml",
placeholder: t("state.bulk_mode_placeholder").toString(),
},
watch: {
params$: {
handler(newValue) {
linter: null,
completer: null,
})
const params$ = useReadonlyStream(restParams$, [])
watch(
params$,
(newValue) => {
if (
(newValue[newValue.length - 1]?.key !== "" ||
newValue[newValue.length - 1]?.value !== "") &&
newValue.length
)
this.addParam()
addParam()
},
deep: true,
},
},
// mounted() {
// if (!this.params$?.length) {
// this.addParam()
// }
// },
methods: {
addParam() {
{ deep: true }
)
const addParam = () => {
addRESTParam({ key: "", value: "", active: true })
},
updateParam(index: number, item: HoppRESTParam) {
}
const updateParam = (index: number, item: HoppRESTParam) => {
updateRESTParam(index, item)
},
deleteParam(index: number) {
}
const deleteParam = (index: number) => {
deleteRESTParam(index)
},
clearContent() {
}
const clearContent = () => {
deleteAllRESTParams()
},
},
})
}
const EXPERIMENTAL_URL_BAR_ENABLED = useSetting("EXPERIMENTAL_URL_BAR_ENABLED")
</script>