Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
2
2021-155
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
2021-155
2021-155
Commits
79c3cb92
Commit
79c3cb92
authored
Oct 15, 2021
by
dasunx
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Automated answer content updated
parent
fbd26b5d
Changes
26
Hide whitespace changes
Inline
Side-by-side
Showing
26 changed files
with
446 additions
and
46 deletions
+446
-46
backend/controllers/automated-answer.js
backend/controllers/automated-answer.js
+0
-1
backend/controllers/questions.js
backend/controllers/questions.js
+1
-1
backend/index.js
backend/index.js
+0
-1
backend/models/automatedAnswer.js
backend/models/automatedAnswer.js
+9
-1
backend/package-lock.json
backend/package-lock.json
+1
-1
backend/package.json
backend/package.json
+3
-3
backend/python/auto-answer/database.py
backend/python/auto-answer/database.py
+4
-1
backend/python/auto-answer/scrapper.py
backend/python/auto-answer/scrapper.py
+3
-13
backend/python/auto-answer/stof.py
backend/python/auto-answer/stof.py
+11
-4
backend/python/auto-answer/youtube.py
backend/python/auto-answer/youtube.py
+1
-0
client/components/automated-answer-container/index.js
client/components/automated-answer-container/index.js
+44
-12
client/components/automated-answer/index.js
client/components/automated-answer/index.js
+13
-0
client/components/automated-answer/no-automated-answer/index.js
.../components/automated-answer/no-automated-answer/index.js
+11
-3
client/components/automated-answer/no-automated-answer/no-automated-answer.module.css
...answer/no-automated-answer/no-automated-answer.module.css
+7
-0
client/components/blog-article/BlogArticle.jsx
client/components/blog-article/BlogArticle.jsx
+19
-0
client/components/blog-article/BlogArticle.module.css
client/components/blog-article/BlogArticle.module.css
+132
-0
client/components/blogs-wrapper/BlogsWrapper.jsx
client/components/blogs-wrapper/BlogsWrapper.jsx
+38
-0
client/components/blogs-wrapper/BlogsWrapper.module.css
client/components/blogs-wrapper/BlogsWrapper.module.css
+16
-0
client/components/icons/Eye.js
client/components/icons/Eye.js
+29
-0
client/components/icons/EyeClose.js
client/components/icons/EyeClose.js
+59
-0
client/components/pagination/Pagination.jsx
client/components/pagination/Pagination.jsx
+2
-2
client/components/pagination/Pagination.module.css
client/components/pagination/Pagination.module.css
+7
-1
client/components/question-ask-view/question-form/index.js
client/components/question-ask-view/question-form/index.js
+0
-1
client/components/show-hide/ShowHide.jsx
client/components/show-hide/ShowHide.jsx
+22
-0
client/components/show-hide/ShowHide.module.css
client/components/show-hide/ShowHide.module.css
+14
-0
client/styles/variables.css
client/styles/variables.css
+0
-1
No files found.
backend/controllers/automated-answer.js
View file @
79c3cb92
...
...
@@ -47,7 +47,6 @@ exports.requestAutomatedAnswer = async (req, res, next) => {
*/
exports
.
getAutomatedAnswer
=
async
(
req
,
res
,
next
)
=>
{
const
{
qid
}
=
req
.
params
;
console
.
log
(
'
answer is here
'
+
qid
);
try
{
const
answer
=
await
AutomatedAnswer
.
findOne
({
question
:
qid
});
if
(
!
answer
)
{
...
...
backend/controllers/questions.js
View file @
79c3cb92
...
...
@@ -34,7 +34,7 @@ exports.createQuestion = async (req, res, next) => {
text
});
res
.
status
(
201
).
json
(
question
);
const
autoAnswer
=
await
AutomatedAnswer
.
create
({
question
:
question
.
_id
,
loading
:
true
});
const
autoAnswer
=
await
AutomatedAnswer
.
create
({
question
:
question
.
_id
});
const
pythonScript
=
spawn
(
'
python
'
,
[
path
.
join
(
__dirname
,
'
..
'
,
'
python
'
,
'
auto-answer
'
,
'
scrapper.py
'
),
title
,
...
...
backend/index.js
View file @
79c3cb92
...
...
@@ -2,7 +2,6 @@ const app = require('./app');
const
mongoose
=
require
(
'
mongoose
'
);
const
config
=
require
(
'
./config
'
);
const
connect
=
(
url
)
=>
{
return
mongoose
.
connect
(
url
,
config
.
db
.
options
);
};
...
...
backend/models/automatedAnswer.js
View file @
79c3cb92
...
...
@@ -62,7 +62,15 @@ const AutomatedAnswerSchema = mongoose.Schema({
{
type
:
String
}
]
],
isLoading
:
{
type
:
Boolean
,
default
:
true
},
isComplete
:
{
type
:
Boolean
,
default
:
false
}
});
module
.
exports
=
mongoose
.
model
(
'
AutomatedAnswer
'
,
AutomatedAnswerSchema
);
backend/package-lock.json
View file @
79c3cb92
{
"name"
:
"
stackoverflow-api
"
,
"name"
:
"
probexpert-be
"
,
"version"
:
"1.0.0"
,
"lockfileVersion"
:
1
,
"requires"
:
true
,
...
...
backend/package.json
View file @
79c3cb92
{
"name"
:
"
stackoverflow-api
"
,
"name"
:
"
probexpert-be
"
,
"version"
:
"1.0.0"
,
"description"
:
"
Stackoverflow Clone Server
"
,
"description"
:
"
Probexpert backend
"
,
"main"
:
"index.js"
,
"scripts"
:
{
"start"
:
"node index.js"
,
...
...
@@ -14,7 +14,7 @@
"Rest"
,
"MERN"
],
"author"
:
"
Salih Ozdemir
"
,
"author"
:
"
Dasun Ekanayake
"
,
"license"
:
"ISC"
,
"dependencies"
:
{
"bcryptjs"
:
"^2.4.3"
,
...
...
backend/python/auto-answer/database.py
View file @
79c3cb92
import
certifi
ca
=
certifi
.
where
()
DATABASE_URL_PROD
=
"mongodb+srv://admin2:admin12345@cluster0.u4vl4.mongodb.net/production?retryWrites=true&w=majority"
DATABASE_URL_DEV
=
"mongodb+srv://admin:admin1234@cluster0.u4vl4.mongodb.net/test?retryWrites=true&w=majority"
...
...
@@ -15,7 +18,7 @@ def get_database():
CONNECTION_STRING
=
ENV
==
"DEV"
and
DATABASE_URL_DEV
or
DATABASE_URL_PROD
# Create a connection using MongoClient. You can import MongoClient or use pymongo.MongoClient
client
=
MongoClient
(
CONNECTION_STRING
)
client
=
MongoClient
(
CONNECTION_STRING
,
tlsCAFile
=
ca
)
# Create the database for our example (we will use the same database throughout the tutorial
return
ENV
==
"DEV"
and
client
[
"test"
]
or
client
[
"production"
]
backend/python/auto-answer/scrapper.py
View file @
79c3cb92
...
...
@@ -17,7 +17,8 @@ def saveAnswer(ans_id, stackoverflow, videos, medium_r, dev_r, github_r):
{
"_id"
:
ObjectId
(
ans_id
)},
{
"$set"
:
{
"loading"
:
False
,
"isLoading"
:
False
,
"isComplete"
:
True
,
"youtube"
:
videos
,
"stackoverflow"
:
stackoverflow
,
"medium_articles"
:
medium_r
.
get
(
"blogs"
,
[]),
...
...
@@ -29,18 +30,7 @@ def saveAnswer(ans_id, stackoverflow, videos, medium_r, dev_r, github_r):
}
},
)
print
(
{
"youtube"
:
videos
,
"stackoverflow"
:
stackoverflow
,
"medium_articles"
:
medium_r
[
"blogs"
],
"dev_articles"
:
dev_r
[
"blogs"
],
"medium_resources"
:
medium_r
[
"resources"
],
"dev_resources"
:
dev_r
[
"resources"
],
"github_repos"
:
github_r
[
"repos"
],
"github_links"
:
github_r
[
"links"
],
}
)
except
NameError
as
err
:
print
(
"ERRORRR"
)
print
(
err
)
...
...
backend/python/auto-answer/stof.py
View file @
79c3cb92
...
...
@@ -73,7 +73,14 @@ class STOF:
# print(soup.prettify().encode("utf-8"))
return
answer
def
calculateAccuracy
(
self
):
"""
Compare the user's question with stackoverflow question and calculate the accuracy
"""
\ No newline at end of file
def
calculateAccuracy
(
self
):
"""
Compare the user's question with stackoverflow question and calculate the accuracy
"""
pass
def
get_clean_url
(
url
):
import
re
pattern
=
r"^.*?\&sa="
return
re
.
match
(
pattern
,
url
)
.
group
(
0
)
backend/python/auto-answer/youtube.py
View file @
79c3cb92
...
...
@@ -27,3 +27,4 @@ class Youtube:
videos
.
append
(
i
[
"link"
])
print
(
i
[
"link"
])
return
videos
\ No newline at end of file
client/components/automated-answer-container/index.js
View file @
79c3cb92
...
...
@@ -9,6 +9,7 @@ import styles from './automated-answer-container.module.css'
const
AutomatedAnswerContainer
=
({
question_id
})
=>
{
const
[
loading
,
setLoading
]
=
useState
(
true
)
const
[
answer
,
setAnswer
]
=
useState
()
const
[
isAnswerGenerating
,
setIsAnswertGenerating
]
=
useState
(
false
)
const
[
error
,
setError
]
=
useState
({
status
:
''
,
action
:
''
,
...
...
@@ -20,8 +21,16 @@ const AutomatedAnswerContainer = ({ question_id }) => {
const
fetchAutomatedAnswer
=
async
()
=>
{
try
{
const
response
=
await
publicFetch
.
get
(
`automatedanswer/
${
question_id
}
`
)
if
(
response
.
status
==
200
)
setAnswer
(
response
.
data
)
else
setServerError
({
response
})
if
(
response
.
status
==
200
)
{
console
.
log
(
'
RESPONSE IS HERE AND IT IS
'
)
const
{
isLoading
,
isComplete
}
=
response
.
data
.
automatedanswer
if
(
isLoading
&&
!
isComplete
)
{
setIsAnswertGenerating
(
true
)
setServerError
(
102
)
}
else
{
setAnswer
(
response
.
data
)
}
}
else
setServerError
({
response
})
}
catch
(
error
)
{
setServerError
(
error
)
}
...
...
@@ -31,7 +40,14 @@ const AutomatedAnswerContainer = ({ question_id }) => {
},
[
question_id
])
const
setServerError
=
(
error
)
=>
{
if
(
error
.
response
.
status
==
404
)
{
if
(
error
==
102
)
{
setError
({
status
:
'
102
'
,
action
:
'
loading
'
,
button
:
'
Answer is generatingg
'
,
message
:
'
Automated answer 🤖 is generating in the backend
'
})
}
else
if
(
error
.
response
.
status
==
404
)
{
setError
({
status
:
'
404
'
,
action
:
'
create
'
,
...
...
@@ -48,6 +64,30 @@ const AutomatedAnswerContainer = ({ question_id }) => {
}
}
const
getBody
=
()
=>
{
if
(
loading
)
{
return
<
Spinner
className
=
{
styles
.
spinner
}
/
>
}
else
if
(
isAnswerGenerating
)
{
return
(
<
NoAutomatedAnswer
question_id
=
{
question_id
}
error
=
{
error
}
isGenerating
=
{
true
}
/
>
)
}
else
if
(
answer
!=
null
)
{
return
<
AutomatedAnswer
automatedAnswer
=
{
answer
.
automatedanswer
}
/
>
}
else
{
return
(
<
NoAutomatedAnswer
question_id
=
{
question_id
}
error
=
{
error
}
isGenerating
=
{
false
}
/
>
)
}
}
return
(
<
div
className
=
{
styles
.
container
}
>
<
div
className
=
{
styles
.
header
}
>
...
...
@@ -55,15 +95,7 @@ const AutomatedAnswerContainer = ({ question_id }) => {
<
h2
>
Automated
Answer
<
/h2
>
<
/div
>
<
/div
>
<
div
className
=
{
styles
.
wrapper
}
>
{
loading
?
(
<
Spinner
className
=
{
styles
.
spinner
}
/
>
)
:
answer
!=
null
?
(
<
AutomatedAnswer
automatedAnswer
=
{
answer
.
automatedanswer
}
/
>
)
:
(
<
NoAutomatedAnswer
question_id
=
{
question_id
}
error
=
{
error
}
/
>
)}
<
/div
>
<
div
className
=
{
styles
.
wrapper
}
>
{
getBody
()}
<
/div
>
<
/div
>
)
}
...
...
client/components/automated-answer/index.js
View file @
79c3cb92
import
React
from
'
react
'
import
BlogsWrapper
from
'
../blogs-wrapper/BlogsWrapper
'
import
StackOverflowAnswer
from
'
../stof-answer
'
import
YoutubeVideoWrapper
from
'
../youtube-videos/YoutubeVideoWrapper
'
...
...
@@ -18,6 +19,18 @@ const AutomatedAnswer = ({ automatedAnswer }) => {
)
:
(
<
h1
>
No
youtubes
found
for
this
question
<
/h1
>
)}
<
BlogsWrapper
source
=
"
Medium
"
articles
=
{
automatedAnswer
.
medium_articles
}
resources
=
{
automatedAnswer
.
medium_resources
}
/
>
<
BlogsWrapper
source
=
"
Dev.to
"
articles
=
{
automatedAnswer
.
dev_articles
}
resources
=
{
automatedAnswer
.
dev_resources
}
/
>
<
/
>
)
}
...
...
client/components/automated-answer/no-automated-answer/index.js
View file @
79c3cb92
import
React
from
'
react
'
import
React
,
{
useContext
}
from
'
react
'
import
{
FetchContext
}
from
'
../../../store/fetch
'
import
styles
from
'
./no-automated-answer.module.css
'
const
NoAutomatedAnswer
=
({
question_id
,
error
})
=>
{
import
{
Spinner
}
from
'
../../icons
'
const
NoAutomatedAnswer
=
({
question_id
,
error
,
isGenerating
})
=>
{
const
{
authAxios
}
=
useContext
(
FetchContext
)
const
{
status
,
action
,
button
,
message
}
=
error
return
(
<
div
className
=
{
styles
.
no_automated_answer
}
>
<
h1
className
=
{
styles
.
title
}
>
{
message
}
<
/h1
>
<
button
className
=
{
styles
.
generate_btn
}
>
{
button
}
<
/button
>
{
isGenerating
?
(
<
Spinner
className
=
{
styles
.
spinner
}
/
>
)
:
(
<
button
className
=
{
styles
.
generate_btn
}
>
{
button
}
<
/button
>
)}
<
/div
>
)
}
...
...
client/components/automated-answer/no-automated-answer/no-automated-answer.module.css
View file @
79c3cb92
...
...
@@ -17,3 +17,10 @@
font-size
:
1.5em
;
text-align
:
center
;
}
.spinner
{
display
:
flex
;
margin
:
auto
;
height
:
3em
;
width
:
3em
;
}
client/components/blog-article/BlogArticle.jsx
0 → 100644
View file @
79c3cb92
import
React
from
'
react
'
import
styles
from
'
./BlogArticle.module.css
'
const
BlogArticle
=
({
article
})
=>
{
const
createMarkup
=
()
=>
{
return
{
__html
:
article
.
description
}
}
return
(
<
div
className=
{
styles
.
blog_article
}
>
<
span
className=
{
styles
.
title
}
>
{
article
.
title
}
</
span
>
<
div
className=
{
styles
.
description
}
dangerouslySetInnerHTML=
{
createMarkup
()
}
></
div
>
</
div
>
)
}
export
default
BlogArticle
client/components/blog-article/BlogArticle.module.css
0 → 100644
View file @
79c3cb92
.blog_article
{
margin
:
1em
0
;
overflow
:
hidden
;
}
.title
{
display
:
block
;
font-size
:
2em
;
text-align
:
center
;
margin
:
10px
0
;
}
.description
{
width
:
100%
;
/* blockquote {
--reach-tabs: 1;
--reach-menu-button: 1;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
color: white;
font-family: medium-content-sans-serif-font, -apple-system,
BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, Cantarell,
'Open Sans', 'Helvetica Neue', sans-serif;
font-weight: 400;
word-break: break-word;
word-wrap: break-word;
box-sizing: inherit;
margin: 0;
box-shadow: inset 3px 0 0 0 rgba(41, 41, 41, 1);
padding-left: 23px;
margin-left: -20px;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
word-wrap: break-word;
box-sizing: inherit;
margin: 0;
font-weight: 400;
word-break: break-word;
font-style: italic;
font-family: charter, Georgia, Cambria, 'Times New Roman', Times, serif;
margin-bottom: -0.46em;
font-size: 21px;
margin-top: 2em;
line-height: 32px;
letter-spacing: -0.003em;
strong {
--reach-tabs: 1;
--reach-menu-button: 1;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
word-wrap: break-word;
word-break: break-word;
color: white;
font-style: italic;
font-size: 21px;
line-height: 32px;
letter-spacing: -0.003em;
box-sizing: inherit;
font-family: charter, Georgia, Cambria, 'Times New Roman', Times, serif;
font-weight: 700;
}
} */
*
{
width
:
100%
;
overflow
:
hidden
;
}
img
{
width
:
100%
;
}
figure
{
img
{
width
:
100%
;
}
figcaption
{
font-size
:
0.8em
;
text-align
:
center
;
color
:
var
(
--black-200
);
}
}
p
{
margin
:
20px
0
;
font-size
:
1.2em
;
}
pre
{
padding
:
20px
;
background-color
:
var
(
black
);
font-size
:
1.1em
;
font-family
:
'Roboto Mono'
,
monospace
!important
;
}
pre
::first-line
{
font-weight
:
bold
;
}
ul
{
margin-left
:
10px
;
padding
:
0
;
list-style
:
none
;
list-style-image
:
none
;
font-size
:
1.1em
;
li
{
letter-spacing
:
-0.003em
;
line-height
:
32px
;
margin-left
:
30px
;
/* margin-top: 2em; */
list-style
:
inside
;
list-style-type
:
disc
!important
;
margin-bottom
:
-0.46em
;
}
}
h4
{
font-size
:
1.3em
;
margin
:
10px
0
;
}
h3
{
font-size
:
1.4em
!important
;
margin
:
20px
0
10px
0
;
}
a
{
color
:
var
(
--blue-300
);
}
a
:hover
{
color
:
var
(
--blue-600
);
}
}
client/components/blogs-wrapper/BlogsWrapper.jsx
0 → 100644
View file @
79c3cb92
import
React
,
{
useState
}
from
'
react
'
import
AutomatedAnswerSwiper
from
'
../automated-answer-swiper/AutomatedAnswerSwiper
'
import
BlogArticle
from
'
../blog-article/BlogArticle
'
import
ShowHide
from
'
../show-hide/ShowHide
'
import
styles
from
'
./BlogsWrapper.module.css
'
const
BlogsWrapper
=
({
source
,
articles
,
resources
})
=>
{
const
[
show
,
setShow
]
=
useState
(
false
)
return
(
<>
{
articles
&&
articles
.
length
>
0
?
(
<>
<
h1
className=
{
styles
.
h1
}
>
Here
{
articles
.
length
>
1
?
'
are
'
:
'
is
'
}
{
articles
.
length
}
article
{
articles
.
length
>
1
&&
'
s
'
}
I found on
{
source
}
<
ShowHide
show=
{
show
}
onClick=
{
()
=>
setShow
(
!
show
)
}
/>
</
h1
>
{
show
&&
(
<
div
className=
{
styles
.
blogs_wrapper
}
>
<
AutomatedAnswerSwiper
>
{
articles
.
map
((
article
,
i
)
=>
{
return
<
BlogArticle
key=
{
i
}
article=
{
article
}
/>
})
}
</
AutomatedAnswerSwiper
>
</
div
>
)
}
</>
)
:
(
<
h1
>
No
{
source
}
articles found for this question. Please refer the extra
resouces to find more info
</
h1
>
)
}
</>
)
}
export
default
BlogsWrapper
client/components/blogs-wrapper/BlogsWrapper.module.css
0 → 100644
View file @
79c3cb92
.blogs_wrapper
{
margin-top
:
0.5em
;
background-color
:
#2d2d2d
;
padding
:
0.8em
;
border-radius
:
2px
;
margin-bottom
:
3em
;
width
:
100%
;
overflow
:
hidden
;
}
.h1
{
font-size
:
2em
!important
;
display
:
flex
;
justify-content
:
space-between
;
align-items
:
center
;
}
client/components/icons/Eye.js
0 → 100644
View file @
79c3cb92
import
React
from
'
react
'
const
EyeIcon
=
({
width
,
height
,
color
})
=>
{
return
(
<
svg
xmlns
=
"
http://www.w3.org/2000/svg
"
version
=
"
1.1
"
id
=
"
Capa_1
"
width
=
{
width
}
height
=
{
height
}
fill
=
{
color
}
viewBox
=
"
0 0 511.992 511.992
"
enableBackground
=
"
new 0 0 512 512
"
>
<
g
>
<
g
>
<
path
d
=
"
M510.096,249.937c-4.032-5.867-100.928-143.275-254.101-143.275C124.56,106.662,7.44,243.281,2.512,249.105 c-3.349,3.968-3.349,9.792,0,13.781C7.44,268.71,124.56,405.329,255.995,405.329S504.549,268.71,509.477,262.886 C512.571,259.217,512.848,253.905,510.096,249.937z M255.995,383.996c-105.365,0-205.547-100.48-230.997-128 c25.408-27.541,125.483-128,230.997-128c123.285,0,210.304,100.331,231.552,127.424 C463.013,282.065,362.256,383.996,255.995,383.996z
"
/>
<
/g
>
<
/g
>
<
g
>
<
g
>
<
path
d
=
"
M255.995,170.662c-47.061,0-85.333,38.272-85.333,85.333s38.272,85.333,85.333,85.333s85.333-38.272,85.333-85.333 S303.056,170.662,255.995,170.662z M255.995,319.996c-35.285,0-64-28.715-64-64s28.715-64,64-64s64,28.715,64,64 S291.28,319.996,255.995,319.996z
"
/>
<
/g
>
<
/g
>
<
/svg
>
)
}
export
default
EyeIcon
client/components/icons/EyeClose.js
0 → 100644
View file @
79c3cb92
import
React
from
'
react
'
const
EyeCloseIcon
=
({
width
,
height
,
color
})
=>
{
return
(
<
svg
xmlns
=
"
http://www.w3.org/2000/svg
"
version
=
"
1.1
"
id
=
"
Capa_1
"
width
=
{
width
}
height
=
{
height
}
fill
=
{
color
}
viewBox
=
"
0 0 511.992 511.992
"
enableBackground
=
"
new 0 0 512 512
"
>
<
g
>
<
g
>
<
path
d
=
"
M316.332,195.662c-4.16-4.16-10.923-4.16-15.083,0c-4.16,4.16-4.16,10.944,0,15.083 c12.075,12.075,18.752,28.139,18.752,45.248c0,35.285-28.715,64-64,64c-17.109,0-33.173-6.656-45.248-18.752 c-4.16-4.16-10.923-4.16-15.083,0c-4.16,4.139-4.16,10.923,0,15.083c16.085,16.128,37.525,25.003,60.331,25.003 c47.061,0,85.333-38.272,85.333-85.333C341.334,233.187,332.46,211.747,316.332,195.662z
"
/>
<
/g
>
<
/g
>
<
g
>
<
g
>
<
path
d
=
"
M270.87,172.131c-4.843-0.853-9.792-1.472-14.869-1.472c-47.061,0-85.333,38.272-85.333,85.333 c0,5.077,0.619,10.027,1.493,14.869c0.917,5.163,5.419,8.811,10.475,8.811c0.619,0,1.237-0.043,1.877-0.171 c5.781-1.024,9.664-6.571,8.64-12.352c-0.661-3.627-1.152-7.317-1.152-11.157c0-35.285,28.715-64,64-64 c3.84,0,7.531,0.491,11.157,1.131c5.675,1.152,11.328-2.859,12.352-8.64C280.534,178.702,276.652,173.155,270.87,172.131z
"
/>
<
/g
>
<
/g
>
<
g
>
<
g
>
<
path
d
=
"
M509.462,249.102c-2.411-2.859-60.117-70.208-139.712-111.445c-5.163-2.709-11.669-0.661-14.379,4.587 c-2.709,5.227-0.661,11.669,4.587,14.379c61.312,31.744,110.293,81.28,127.04,99.371c-25.429,27.541-125.504,128-230.997,128 c-35.797,0-71.872-8.64-107.264-25.707c-5.248-2.581-11.669-0.341-14.229,4.971c-2.581,5.291-0.341,11.669,4.971,14.229 c38.293,18.496,77.504,27.84,116.523,27.84c131.435,0,248.555-136.619,253.483-142.443 C512.854,258.915,512.833,253.091,509.462,249.102z
"
/>
<
/g
>
<
/g
>
<
g
>
<
g
>
<
path
d
=
"
M325.996,118.947c-24.277-8.171-47.829-12.288-69.995-12.288c-131.435,0-248.555,136.619-253.483,142.443 c-3.115,3.669-3.371,9.003-0.597,12.992c1.472,2.112,36.736,52.181,97.856,92.779c1.813,1.216,3.84,1.792,5.888,1.792 c3.435,0,6.827-1.664,8.875-4.8c3.264-4.885,1.92-11.52-2.987-14.763c-44.885-29.845-75.605-65.877-87.104-80.533 c24.555-26.667,125.291-128.576,231.552-128.576c19.861,0,41.131,3.755,63.189,11.157c5.589,2.005,11.648-1.088,13.504-6.699 C334.572,126.862,331.585,120.825,325.996,118.947z
"
/>
<
/g
>
<
/g
>
<
g
>
<
g
>
<
path
d
=
"
M444.865,67.128c-4.16-4.16-10.923-4.16-15.083,0L67.116,429.795c-4.16,4.16-4.16,10.923,0,15.083 c2.091,2.069,4.821,3.115,7.552,3.115c2.731,0,5.461-1.045,7.531-3.115L444.865,82.211 C449.025,78.051,449.025,71.288,444.865,67.128z
"
/>
<
/g
>
<
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
g
><
/g
>
<
/svg
>
)
}
export
default
EyeCloseIcon
client/components/pagination/Pagination.jsx
View file @
79c3cb92
...
...
@@ -11,7 +11,7 @@ const Pagination = ({
return
(
<
div
className=
{
styles
.
pagination_wrapper
}
>
<
span
onClick=
{
onClickFirst
}
className=
{
styles
.
cursor
}
>
first
<<
</
span
>
<
div
className=
{
styles
.
numbering
}
>
{
new
Array
(
length
).
fill
(
0
).
map
((
item
,
index
)
=>
{
...
...
@@ -33,7 +33,7 @@ const Pagination = ({
<span className={styles.muted_number}>{length}</span> */
}
</
div
>
<
span
onClick=
{
onClickLast
}
className=
{
styles
.
cursor
}
>
last
>>
</
span
>
</
div
>
)
...
...
client/components/pagination/Pagination.module.css
View file @
79c3cb92
.pagination_wrapper
{
display
:
flex
;
flex-direction
:
row
;
justify-content
:
space-between
;
justify-content
:
center
;
align-items
:
center
;
}
.numbering
{
...
...
@@ -27,5 +28,10 @@
}
.cursor
{
margin
:
0
10px
;
cursor
:
pointer
;
color
:
#fff
;
padding
:
4px
10px
;
background-color
:
#2d2d2d
;
border
:
1px
solid
#78ff78
;
}
client/components/question-ask-view/question-form/index.js
View file @
79c3cb92
...
...
@@ -10,7 +10,6 @@ import Textarea from '../../textarea'
import
FormInput
from
'
../../form-input
'
import
TagInput
from
'
../../tag-input
'
import
SimilarQuestionSuggestions
from
'
../../similar-question-suggestions
'
import
styles
from
'
./question-form.module.css
'
const
QuestionForm
=
()
=>
{
...
...
client/components/show-hide/ShowHide.jsx
0 → 100644
View file @
79c3cb92
import
React
from
'
react
'
import
EyeIcon
from
'
../icons/Eye
'
import
EyeCloseIcon
from
'
../icons/EyeClose
'
import
styles
from
'
./ShowHide.module.css
'
const
ShowHide
=
({
onClick
,
show
})
=>
{
return
(
<
div
onClick=
{
onClick
}
className=
{
styles
.
show_hide
}
>
{
show
?
(
<
span
>
<
EyeCloseIcon
width=
{
24
}
height=
{
24
}
color=
"red"
/>
Hide
</
span
>
)
:
(
<
span
>
<
EyeIcon
width=
{
24
}
height=
{
24
}
color=
"white"
/>
Show
</
span
>
)
}
</
div
>
)
}
export
default
ShowHide
client/components/show-hide/ShowHide.module.css
0 → 100644
View file @
79c3cb92
.show_hide
{
cursor
:
pointer
;
font-size
:
1.5rem
;
background-color
:
var
(
--black-800
);
padding
:
2px
10px
;
border-radius
:
5px
;
span
{
display
:
flex
;
align-items
:
center
;
*
{
margin-right
:
5px
;
}
}
}
client/styles/variables.css
View file @
79c3cb92
...
...
@@ -29,6 +29,5 @@
--powder-700
:
#39739d
;
--powder-800
:
#2c5777
;
--main-purple
:
#800080
;
--fade
:
120ms
;
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment