webForumDet fria alternativet

Chatbot - Direkt på webbsidan

ASP

23 svar · 1 261 visningar · startad av medialabs

Medlem sedan mars 20023 686 inlägg
Frågan#1

Hej!

Hittade en ganska simpel (och det enda i asp) som fungerar som en Chat-bot. Men den är som sagt ganska simpel i sitt utförande, vilket är bra, men den är inte allt för smart ;)

Har några problem som jag behöver hjälp med att övervinna.

Om ordet eller meningen innehåller en storbokstav och den motsvarande bokstaven som den jämför med är "liten" så känner den inte igen. Exempel: Användaren skriver in: Hej och boten känner igen: hej och returnerar således: "Jag har tyvärr svårt att förstå din fråga. Försök formulera om frågan." Hur gör man så att det inte spelar någon roll om det är stora eller små bokstäver.

Jag vill göra något form av filter så att svärord filtreras bort och användaren får svaret: Jag är här för att svara på seriösa frågor. som det är nu så måste jag lägga in varje svärord på en egen "frågelinje".

Går det att göra Chatt-boten databasdriven istället? Känns mycket smidigare att snabbt och enkelt kunna lägga till frågor och svar i en databas istället för att skapa hundratals rader på aspsidan.

alla tips och förbättringar emottages!!

Chatform.asp

<%
' Little chat bot for your site
' Chat Form
' by Rodrigo S. Alhadeff, 1/2001
' About the Author: Rodrigo S. Alhadeff is the Founder & Senior Programmer of Comersus Shopping Cart, www.comersus.com
%>
<HTML><title>Chat Bot</title> 
<p><b>Ask our Bot</b></p>
<FORM name="" action="chatBot.asp" method="post">
  <table width="526" border="0">
    <tr> 
      <td width="132"> 
        <p><br>
          <img src="bot.jpg" width="120" height="140"></p>
        <p> </p>
      </td>
      <td width="384"> 
        <p><%response.write request.querystring("botResponse")%></p>
        <p><i>Please enter your question</i></p>
        <p> 
          <textarea name="userText" cols="40" rows="3"></textarea>
        </p>
      </td>
    </tr>
    <tr> 
      <td width="132"> 
        <input type="submit" name="Submit" value="Ställ din fråga!">
      </td>
      <td width="384"> </td>
    </tr>
  </table>
  </FORM>
</HTML>

Chatbot.asp

<%

on error resume next

dim userText, botAnswer, upLimit, botResponse

' change for more Brain lines

upLimit    = 11

redim brain(upLimit,2)

call loadBrain()

' get user text 

userText	= request.form("userText")
botAnswer	= ""

' locate answer

for f=0 to upLimit          
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next

' print response

if userText="" then
  botResponse="Du glömde fylla i en fråga!"  
else

 botResponse="Q: " & userText &""

 if botAnswer="" then
    botResponse=botResponse&"<br>A: Jag har tyvärr svårt att förstå din fråga. Försök formulera om frågan. "   
 else
    botResponse=botResponse&"<br>A: "&botAnswer
 end if
 
end if

response.redirect "chatForm.asp?botResponse="&Server.UrlEncode(botResponse)

sub loadBrain()

' sub that load questions and answers

' the (x,0) line contains the text you want to recognize
' the (x,1) line contains bot response
' if you add more lines please increase upLimit variable

 brain(0,0) = "En fråga"
 brain(0,1) = "ett svar"
 
 brain(1,0) = "hjälp"
 brain(1,1) = "Du kan få hjälp genom vårt forum, länk hittar du i menyn till vänster."
 
 brain(2,0) = "hej"
 brain(2,1) = "Hej!"
 
 brain(3,0) = "brandvägg"
 brain(3,1) = "Du hittar en lista på brandväggar som är gratis under 'Verktyg' i menyn."
 
 brain(4,0) = "tack"
 brain(4,1) = "Varsågod."

 brain(5,0) = "heter"
 brain(5,1) = "Mitt namn är Emma."

 brain(6,0) = "namn"
 brain(6,1) = "Mitt namn är Emma."

 brain(7,0) = "du"
 brain(7,1) = "Mitt namn är Emma."

 brain(8,0) = "svärord1 svärord2 svärord3 svärord4 svärord5 svärord6 svärord7"
 brain(8,1) = "Jag är här för att svara på seriösa frågor."

 brain(9,0) = "ok"
 brain(9,1) = "Okej då!"

 brain(10,0) = "Fråga"
 brain(10,1) = "svar"

 brain(11,0) = "Fråga"
 brain(11,1) = "svar"
  
end sub

%>

Testa själva, har lagt upp den på projektserver:
http://relic.securityfocus.se/chatt-bot/chatform.asp

All hjälp och förbättringar mottages med öppna armar! :)

Medlem sedan juni 20031 837 inlägg
#2

byt

<textarea name="userText" cols="40" rows="3"></textarea>

mot

<input type="test" name="userText">

så kan man trycka på enter istället för att behöva klicka på knappen.

vet tyvärr inte vad funktionen för att göra om till små boksäver heter men det brukar vara något i stil med lcase(sträng) eller sträng.toLower()

Medlem sedan mars 20023 686 inlägg
#3

The_Hulk skrev:

byt

<textarea name="userText" cols="40" rows="3"></textarea>

mot

<input type="test" name="userText">

så kan man trycka på enter istället för att behöva klicka på knappen.

vet tyvärr inte vad funktionen för att göra om till små boksäver heter men det brukar vara något i stil med lcase(sträng) eller sträng.toLower()

Tack! Ska ändra rutan till textruta istället som du föreslår.

Skulle fortfarande behöva hjälp så att den inte är känslig för stora och små bokstäver.

Skulle vara smidigare om man kunde lägga in en massa svar osv i en databas istället.

Medlem sedan jan. 20023 327 inlägg
#4

Problemet med att din chat-bot inte känner igen Hej men känner igen hej är enkelt att lösa.

Använd funktionen LCase:

' get user text 

userText	= LCase(request.form("userText"))
botAnswer	= ""

Detta förutsätter förstås att du lagrar chat-botens nyckelord med små bokstäver.

Att göra boten databas-driven är inte heller några problem. Jag kan inte komma med perfekt kod (länge sedan jag sysslade med klassisk asp) men ungefäre så här hade jag gjort.

Först en databastabell med följande attribut:
id, question, answer

Variabeln upLimit får du sätta genom ett databasanrop där du hämtar antalet rader (int) i din tabell för chat-boten. Du får göra om suben LoadBrain så att den hämtar alla frågor och svar från din databas. Därefter skulle du kunna skapa arrayen dynamiskt med hjälp av en loop.

i = 0
j = 0
While NOT rs.EOF
 
    If j = 1 Then
        brain(i,j) = 'ett svar hämta från rs
        i = i + 1
        j = j - 1
        rs.Next()
    Else
        brain(i,j) = 'en fråga hämta från rs
        j = j + 1
    End If
Wend
%>
Medlem sedan mars 20023 686 inlägg
#5

Compusa skrev:

Problemet med att din chat-bot inte känner igen Hej men känner igen hej är enkelt att lösa.

Använd funktionen LCase:

' get user text 

userText	= LCase(request.form("userText"))
botAnswer	= ""

Detta förutsätter förstås att du lagrar chat-botens nyckelord med små bokstäver.

Att göra boten databas-driven är inte heller några problem. Jag kan inte komma med perfekt kod (länge sedan jag sysslade med klassisk asp) men ungefäre så här hade jag gjort.

Först en databastabell med följande attribut:
id, question, answer

Variabeln upLimit får du sätta genom ett databasanrop där du hämtar antalet rader (int) i din tabell för chat-boten. Du får göra om suben LoadBrain så att den hämtar alla frågor och svar från din databas. Därefter skulle du kunna skapa arrayen dynamiskt med hjälp av en loop.

i = 0
j = 0
While NOT rs.EOF()
 
    If j = 1 Then
        brain(i,j) = 'ett svar hämta från rs
        i = i + 1
        j = j - 1
        rs.Next()
    Else
        brain(i,j) = 'en fråga hämta från rs
        j = j + 1
    End If
Wend
%>

Tack, har nu lyckats iaf få fram totala antalet rader i databasen så att Variabeln upLimit får rätt antal rader.

Men jag vet bara inte riktigt huur jag ska skriva om suben LoadBrain så att den hämtar alla frågor och svar från databasen.

Medlem sedan jan. 20023 327 inlägg
#6

Hur ser din tabell ut? Enligt mitt förslag eller annat? Den koden jag skrev i mitt förra inlägg är en god bit på väg tror jag.

Om du har använt dig av den tabell-struktur jag föreslog så skullesql-frågan och loadBrain kunna se ut något sådant här...

SELECT question, answer FROM chatbot
<%
sub loadBrain() 
'Du får lägga till anslutning mot databasen och fylla dit rs med resultatet av sql-frågan här

Dim i, j
i = 0
j = 0
While NOT rs.EOF() 'loopa igenom rs och spara i arrayen
 
    If j = 1 Then
        brain(i,j) = rs("answer")
        i = i + 1
        j = j - 1
        rs.MoveNext
    Else
        brain(i,j) = rs("question")
        j = j + 1
    End If
Wend

end sub
%>

Koden är inte testad, och mina kunskaper i klassisk asp är ringrostiga, men detta är ett gott steg på vägen. Mycket mer ska inte behöva göras.

Medlem sedan mars 20023 686 inlägg
#7

Compusa skrev:

Hur ser din tabell ut? Enligt mitt förslag eller annat? Denna koden jag skrev i mitt förra inlägg är en god bit på väg tror jag.

MySQL: tblassistent
helpid (int10, autoincreasment)
helpquestion (Long text)
helpanswer (Long text)

<%
'on error resume next

Set AssistentConnection = Server.CreateObject("ADODB.Connection")
AssistentConnection.Open "DRIVER={MySQL ODBC 3.51 Driver}; SERVER=; DATABASE=; USER=; PASSWORD=; OPTION=3;"

	Set rsTotalt = Server.CreateObject("ADODB.Recordset")

	sqlTotalt = "SELECT COUNT(*) FROM tblassistent"
	set rsTotalt = AssistentConnection.execute(sqlTotalt)

' change for more Brain lines

upLimit    = RSTotalt(0)

redim brain(upLimit,2)

call loadBrain()

' get user text 

userText	= LCase(request.form("userText"))
botAnswer	= ""
RefUrl 		= request.form("refurl")

' locate answer

for f=0 to upLimit          
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next

' print response

if userText="" then
  botResponse="Du glömde fylla i en fråga!"  
else

 botResponse="<b>Du skrev:</b> <i>" & userText &" </i>"

 if botAnswer="" then
    botResponse=botResponse&"<br><br>Jag har tyvärr svårt att förstå din fråga. Försök formulera om frågan. "   
 else
    botResponse=botResponse&"<br><br>"&botAnswer
 end if
 
end if

response.redirect RefUrl&"?botResponse="&Server.UrlEncode(botResponse)&"&#webbassistent"

sub loadBrain()

' sub that load questions and answers
' the (x,0) line contains the text you want to recognize
' the (x,1) line contains bot response
' if you add more lines please increase upLimit variable

			Set ConnectGet = Server.CreateObject("ADODB.Connection")
			ConnectGet.Open "DRIVER={MySQL ODBC 3.51 Driver}; SERVER=; DATABASE=; USER=; PASSWORD=; OPTION=3;"

			SQLGet = "SELECT * FROM tblassistent"
			set RSGet = ConnectGet.Execute (SQLGet)

i = 0
j = 0
While NOT [B]RSGet.EOF()[/B]
 
    If j = 1 Then
        brain(i,j) = RSGet("helpanswer")
        i = i + 1
        j = j - 1
        RSGet.Next()
    Else
        brain(i,j) = RSGet("helpquestion")
        j = j + 1
    End If
Wend

  
end sub

%>

Resulterar i:

Microsoft VBScript runtime error '800a01c2'

Wrong number of arguments or invalid property assignment: 'RSGet.EOF'

/chatbot_MySQL.asp, line 77

Tänker jag fel nu eller?

Och om jag tar bort paranteserna vid RSGet.EOF så får jag fram detta istället:

Microsoft VBScript runtime error '800a01b6'

Object doesn't support this property or method: 'RSGet.next'

/chatbot_MySQL.asp, line 83

Medlem sedan jan. 20023 327 inlägg
#8

Ändra RSGet.EOF() till RSGet.EOF
Ändra RSGet.Next() till RS.MoveNext

Dvs...

While NOT RSGet.EOF
 
    If j = 1 Then
        brain(i,j) = RSGet("helpanswer")
        i = i + 1
        j = j - 1
        RSGet.MoveNext
    Else
        brain(i,j) = RSGet("helpquestion")
        j = j + 1
    End If
Wend

Jag skulle även rekommendera dig att ändra din sql-query till

SELECT helpanswer, helpquestion FROM tblassistent

Återkom med eventuella fellmeddelanden när du gjort följande ändringar. Har även uppdaterat mitt förra inlägg med lite kod, men du verkar vara på rätt väg i alla fall.

Medlem sedan mars 20023 686 inlägg
#9

Nu börjar vi närma oss, Den kör allt normalt, inga felmeddelanden men den hittar inga frågor/svar, utan svarar: Jag har tyvärr svårt att förstå din fråga. Försök formulera om frågan. Varje gång jag skriver in en fråga. Det finns tre frågor/svar inlagda:

fråga1 - svar1
fråga2 - svar2
fråga3 - svar3

Spelar ingen roll vilken fråga du skriver in, den skriver bara ut: Jag har tyvärr svårt att förstå din fråga. Försök formulera om frågan.

sub loadBrain()

' sub that load questions and answers
' the (x,0) line contains the text you want to recognize
' the (x,1) line contains bot response
' if you add more lines please increase upLimit variable

			Set ConnectGet = Server.CreateObject("ADODB.Connection")
			ConnectGet.Open "DRIVER={MySQL ODBC 3.51 Driver}; SERVER=; DATABASE=; USER=; PASSWORD=; OPTION=3;"

			SQLGet = "SELECT helpanswer, helpquestion FROM tblassistent"
			set RSGet = ConnectGet.Execute (SQLGet)

i = 0
j = 0
While NOT RSGet.EOF
 
    If j = 1 Then
        brain(i,j) = RSGet("helpanswer")
        i = i + 1
        j = j - 1
        RSGet.MoveNext
    Else
        brain(i,j) = RSGet("helpquestion")
        j = j + 1
    End If
Wend

  
end sub
Medlem sedan jan. 20023 327 inlägg
#10

Okej, det verkar som att arrayen kanske inte initieras på rätt sätt. Testa att skriva ut lite.. Har lagt till lite i din kod nedan. Kolla även att värdet i upLimit är korrekt, på samma vis.

sub loadBrain()

' sub that load questions and answers
' the (x,0) line contains the text you want to recognize
' the (x,1) line contains bot response
' if you add more lines please increase upLimit variable

			Set ConnectGet = Server.CreateObject("ADODB.Connection")
			ConnectGet.Open "DRIVER={MySQL ODBC 3.51 Driver}; SERVER=; DATABASE=; USER=; PASSWORD=; OPTION=3;"

			SQLGet = "SELECT helpanswer, helpquestion FROM tblassistent"
			set RSGet = ConnectGet.Execute (SQLGet)

i = 0
j = 0
While NOT RSGet.EOF
 
    If j = 1 Then
        brain(i,j) = RSGet("helpanswer") 'endast för felsökning
        response.write brain(i, j)
        i = i + 1
        j = j - 1
        RSGet.MoveNext
    Else
        brain(i,j) = RSGet("helpquestion")
        response.write brain(i, j) 'endast för felsökning felsökning
        j = j + 1
    End If
Wend

  
end sub
Medlem sedan mars 20023 686 inlägg
#11

Var tvungen att sätta en response.end innan end sub så fick jag fram: fråga1svar1fråga2svar2fråga3svar3, annars körde den allt "normalt", dvs, Jag har tyvärr svårt att förstå din fråga. Försök formulera om frågan.

Medlem sedan jan. 20023 327 inlägg
#12

Har du lust att posta den uppdaterade versionen av boten dvs inte bara loadBrain? Det känns som det är en liten detalj som gör att det inte fungerar riktigt..

Medlem sedan mars 20023 686 inlägg
#13

Compusa skrev:

Har du lust att posta den uppdaterade versionen av boten dvs inte bara loadBrain?

Detta är chatbot_MySQL.asp

<%
'on error resume next

Set AssistentConnection = Server.CreateObject("ADODB.Connection")
AssistentConnection.Open "DRIVER={MySQL ODBC 3.51 Driver}; SERVER=; DATABASE=; USER=; PASSWORD=; OPTION=3;"

	Set rsTotalt = Server.CreateObject("ADODB.Recordset")

	sqlTotalt = "SELECT COUNT(*) FROM tblassistent"
	set rsTotalt = AssistentConnection.execute(sqlTotalt)

' change for more Brain lines

upLimit    = RSTotalt(0)

redim brain(upLimit,2)

call loadBrain()

' get user text 

userText	= LCase(request.form("userText"))
botAnswer	= ""
RefUrl 		= request.form("refurl")

' locate answer

for f=0 to upLimit          
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next

' print response

if userText="" then
  botResponse="Du glömde fylla i en fråga!"  
else

 botResponse="<b>Du skrev:</b> <i>" & userText &" </i>"

 if botAnswer="" then
    botResponse=botResponse&"<br><br>Jag har tyvärr svårt att förstå din fråga. Försök formulera om frågan. "   
 else
    botResponse=botResponse&"<br><br>"&botAnswer
 end if
 
end if

response.redirect RefUrl&"?botResponse="&Server.UrlEncode(botResponse)&"&#webbassistent"

sub loadBrain()

' sub that load questions and answers
' the (x,0) line contains the text you want to recognize
' the (x,1) line contains bot response
' if you add more lines please increase upLimit variable

			Set ConnectGet = Server.CreateObject("ADODB.Connection")
			ConnectGet.Open "DRIVER={MySQL ODBC 3.51 Driver}; SERVER=; DATABASE=; USER=; PASSWORD=; OPTION=3;"

			SQLGet = "SELECT helpanswer, helpquestion FROM tblassistent"
			set RSGet = ConnectGet.Execute (SQLGet)

i = 0
j = 0
While NOT RSGet.EOF
 
    If j = 1 Then
        brain(i,j) = RSGet("helpanswer")
        i = i + 1
        j = j - 1
        RSGet.MoveNext
    Else
        brain(i,j) = RSGet("helpquestion")
        j = j + 1
    End If
Wend

  
end sub

%>
Medlem sedan jan. 20023 327 inlägg
#14

Det känns som felet kan ligga i denna delen, av någon anledning retunerar den alltid falskt/noll.

for f=0 to upLimit          
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next

Kan du på något sätt försöka testa denna funktion med värden som du vet är sanna? Vet ej om datatypen i din tabell kan ställa till med problem men som jag ser det så borde det här fungera eftersom du har värden i din array.

Du är hundra på att du får ut rätt värde av denna?

upLimit    = RSTotalt(0)
response.write upLimit

Ej säker om vbskript är känslig om du blandar med små och stora bokstäver, men borde det inte stå:

upLimit    = rsTotalt(0)

Eftersom du definerar den så på det ställer du tilldelerar den dess värde.

Medlem sedan mars 20023 686 inlägg
#15

Compusa skrev:

Det känns som felet kan ligga i denna delen, av någon anledning retunerar den alltid falskt/noll.

Kan du på något sätt försöka testa denna funktion med värden som du vet är sanna? Vet ej om datatypen i din tabell kan ställa till med problem men som jag ser det så borde det här fungera eftersom du har värden i din array.

Du är hundra på att du får ut rätt värde av denna?

upLimit    = RSTotalt(0)
response.write upLimit

Japp, den returnerar: 3

Ej säker om vbskript är känslig om du blandar med små och stora bokstäver, men borde det inte stå:

upLimit    = rsTotalt(0)

Eftersom du definerar den så på det ställer du tilldelerar den dess värde.

Gjorde ingen skillnad.

Du kan testa webbassistenten: http://www.securityfocus.se/public/webbassistent.asp

Medlem sedan jan. 20023 327 inlägg
#16

Japp, det fungerar inte så bra :(

Skriver den ut något om du gör följande innan denna rad?
Det enda jag kan se är nämligen att du inte får tag på värdena här..

response.write brain(0, 0)
response.write brain(0, 1)
response.write brain(1, 0)
response.write brain(1, 1)
response.write brain(2, 0)
response.write brain(2, 1)
for f=0 to upLimit     
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next
Medlem sedan mars 20023 686 inlägg
#17

Compusa skrev:

Japp, det fungerar inte så bra :(

Skriver den ut något om du gör följande innan denna rad?
Det enda jag kan se är nämligen att du inte får tag på värdena här..

response.write brain(0, 0)
response.write brain(0, 1)
response.write brain(1, 0)
response.write brain(1, 1)
response.write brain(2, 0)
response.write brain(2, 1)
for f=0 to upLimit     
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next

Svaret blir:

fråga1svar1fråga2svar2fråga3svar3

Medlem sedan jan. 20023 327 inlägg
#18

Du förstår jag faktiskt inte varför det inte fungerar? Ja menar, din array har tilldelats rätt värden och dessa behålls. Av någon anledning så fungerar inte jämförelsen i följande del:

for f=0 to upLimit     
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next

eftersom den aldrig hittar någon träff. Kan det ha att göra med att du har svenska vokaler i din tabell dvs fråga1 osv? Testa att byta ut din testdata och se om det kan ha med detta att göra... Jag har testat scriptet utan att blanda in en databas och använt din exemepldata, då fungerar allt som det ska.

Medlem sedan mars 20023 686 inlägg
#19

Compusa skrev:

Du förstår jag faktiskt inte varför det inte fungerar? Ja menar, din array har tilldelats rätt värden och dessa behålls. Av någon anledning så fungerar inte jämförelsen i följande del:

for f=0 to upLimit     
    if instr(userText,brain(f,0))<>0 then
       botAnswer = brain(f,1)      
    end if     
next

eftersom den aldrig hittar någon träff. Kan det ha att göra med att du har svenska vokaler i din tabell dvs fråga1 osv? Testa att byta ut din testdata och se om det kan ha med detta att göra... Jag har testat scriptet utan att blanda in en databas och använt din exemepldata, då fungerar allt som det ska.

Det gjorde ingen skillnad tyvärr. Jag är lika ställd som du är. Jag testade även för skojs skull att byta till en access-databas istället för en MySQL-databas, ingen skillnad där heller.

Medlem sedan jan. 20023 327 inlägg
#20

Ja det är väldigt skumt :(
Kan det vara så att felet ligger i hur värdena du får från formuläret ser ut?

272 ms totalt · 4 externa anrop · v20260731065814-full.a51de22e
125 ms — deklarationer (db)
0 ms — hämta statistik (cache)
144 ms — hämta tråd, inlägg och bilagor (db)
119 ms — ändringar (db)