11import { CID } from 'multiformats/cid'
2- import React from 'react'
2+ import React , { useState } from 'react'
33import { nativeProtocolRegex , pathRegex , subdomainRegex } from '../../lib/regex.js'
4- import { getGatewayRoot } from '../../lib/to-gateway-root.js'
54import { Link } from './link.jsx'
65import type { IpfsUriParts } from '../../lib/regex.js'
76import type { ReactElement } from 'react'
@@ -30,14 +29,14 @@ function FormatHelp (): ReactElement {
3029 </ >
3130 )
3231}
32+
3333interface ValidationMessageProps {
34- cidOrPeerIdOrDnslink ?: IpfsUriParts [ 'cidOrPeerIdOrDnslink' ] ,
34+ cidOrPeerIdOrDnslink : string ,
3535 requestPath : string ,
36- protocol ?: IpfsUriParts [ 'protocol' ] ,
37- children : React . ReactNode
36+ protocol : string
3837}
3938
40- const ValidationMessage : React . FC < ValidationMessageProps > = ( { cidOrPeerIdOrDnslink, requestPath, protocol, children } ) => {
39+ const ValidationMessage : React . FC < ValidationMessageProps > = ( { cidOrPeerIdOrDnslink, requestPath, protocol } ) => {
4140 let errorElement : ReactElement | null = null
4241
4342 if ( requestPath == null || requestPath === '' ) {
@@ -62,9 +61,7 @@ const ValidationMessage: React.FC<ValidationMessageProps> = ({ cidOrPeerIdOrDnsl
6261
6362 if ( errorElement == null ) {
6463 return (
65- < >
66- { children }
67- </ >
64+ < > </ >
6865 )
6966 }
7067
@@ -77,41 +74,73 @@ const ValidationMessage: React.FC<ValidationMessageProps> = ({ cidOrPeerIdOrDnsl
7774 )
7875}
7976
80- const parseInput = ( uri : string ) : Partial < IpfsUriParts > => {
81- const uriMatch = uri . match ( pathRegex ) ?? uri . match ( subdomainRegex ) ?? uri . match ( nativeProtocolRegex )
82- if ( uriMatch ?. groups != null ) {
83- const { protocol, cidOrPeerIdOrDnslink, path } = uriMatch . groups as unknown as IpfsUriParts
84- return { protocol, cidOrPeerIdOrDnslink, path : path ?. trim ( ) ?? undefined }
85- }
77+ export interface CIDInputProps {
78+ requestPath : string
79+ setRequestPath ( val : string ) : void
80+ setInvalid ( invalid : boolean ) : void
81+ }
82+
83+ export function CIDInput ( { requestPath, setRequestPath, setInvalid } : CIDInputProps ) : ReactElement {
84+ let initialProtocol = ''
85+ let initialCid = ''
8686
87- // it may be just a CID
8887 try {
89- CID . parse ( uri )
90- return { protocol : 'ipfs' , cidOrPeerIdOrDnslink : uri }
91- } catch ( _ ) {
92- // ignore.
93- }
88+ const uriMatch = requestPath . match ( pathRegex ) ?? requestPath . match ( subdomainRegex ) ?? requestPath . match ( nativeProtocolRegex )
89+ const { protocol, cidOrPeerIdOrDnslink } = uriMatch ?. groups as unknown as IpfsUriParts
9490
95- return { }
96- }
91+ initialProtocol = protocol
92+ initialCid = cidOrPeerIdOrDnslink
93+ } catch { }
94+
95+ const [ protocol , setProtocol ] = useState ( initialProtocol )
96+ const [ cidOrPeerIdOrDnslink , setCidOrPeerIdOrDnslink ] = useState ( initialCid )
9797
98- export default function InputValidator ( { requestPath } : { requestPath : string } ) : ReactElement {
99- const { protocol, cidOrPeerIdOrDnslink, path } = parseInput ( requestPath )
100- const swPath = `/${ protocol } /${ cidOrPeerIdOrDnslink } ${ path ?? '' } `
98+ function validate ( val : string ) : void {
99+ setRequestPath ( val )
101100
102- function checkInput ( ) : boolean | undefined {
103- if ( protocol == null || cidOrPeerIdOrDnslink == null ) {
104- return false
101+ const uriMatch = val . match ( pathRegex ) ?? val . match ( subdomainRegex ) ?? val . match ( nativeProtocolRegex )
102+ if ( uriMatch ?. groups != null ) {
103+ const { protocol, cidOrPeerIdOrDnslink } = uriMatch . groups as unknown as IpfsUriParts
104+
105+ setProtocol ( protocol )
106+ setCidOrPeerIdOrDnslink ( cidOrPeerIdOrDnslink )
107+ setInvalid ( false )
108+ return
105109 }
106110
107- window . location . href = getGatewayRoot ( ) + swPath
111+ // it may be just a CID
112+ try {
113+ CID . parse ( val )
114+
115+ setProtocol ( 'ipfs' )
116+ setCidOrPeerIdOrDnslink ( val )
117+ setInvalid ( false )
118+ return
119+ } catch {
120+ // ignore
121+ }
122+
123+ setInvalid ( true )
108124 }
109125
110126 return (
111- < div >
112- < ValidationMessage protocol = { protocol } cidOrPeerIdOrDnslink = { cidOrPeerIdOrDnslink } requestPath = { requestPath } >
113- < button id = 'load-directly' className = 'button-reset pv3 tc bn bg-animate bg-teal-muted hover-bg-navy-muted white pointer f4 w-100' onClick = { checkInput } > Load content</ button >
114- </ ValidationMessage >
115- </ div >
127+ < >
128+ < label htmlFor = 'inputContent' className = 'f5 ma0 pb2 teal fw4 db' > CID, Content Path, or URL</ label >
129+ < input
130+ className = 'input-reset bn black-80 bg-white pa3 w-100 mb3'
131+ id = 'inputContent'
132+ name = 'inputContent'
133+ type = 'text'
134+ placeholder = '/ipfs/bafk.../path/to/file'
135+ required
136+ value = { requestPath }
137+ onChange = { ( e ) => validate ( e . target . value ) }
138+ />
139+ < ValidationMessage
140+ protocol = { protocol }
141+ cidOrPeerIdOrDnslink = { cidOrPeerIdOrDnslink }
142+ requestPath = { requestPath }
143+ />
144+ </ >
116145 )
117146}
0 commit comments