Skip to content

Commit

Permalink
Added OpenAi Chat GPT
Browse files Browse the repository at this point in the history
  • Loading branch information
frianasoa committed Dec 22, 2023
1 parent 9ce1868 commit 3c91b71
Show file tree
Hide file tree
Showing 10 changed files with 235 additions and 70 deletions.
144 changes: 107 additions & 37 deletions content/notes/menus.js
Original file line number Diff line number Diff line change
Expand Up @@ -74,39 +74,49 @@ Menus = {
}
items_ai["sep-ai-02"] = "---------";

if(Zotero.ZeNotes.Prefs.getb("bard-api-key")!="")
if(Zotero.ZeNotes.Prefs.getb("bard-api-key")!="" || Zotero.ZeNotes.Prefs.getb("openai-api-key")!="")
{
items_ai["paraphrase-annotation"] = {
name: "Paraphrase annotation",
icon: "fa-repeat",
items: {
"paraphrase-bard": {name: "Using bard", icon: "fa-b"},
}
items: {}
}

items_ai["custom-prompt-on-cell"] = {
name: "Run custom prompt on cell",
icon: "fa-square",
items: {
"custom-prompt-cell-bard": {name: "Using bard", icon: "fa-b"},
}
items: {}
}

items_ai["custom-prompt-on-row"] = {
name: "Run custom prompt on row",
icon: "fa-arrow-right",
items: {
"custom-prompt-row-bard": {name: "Using bard", icon: "fa-b"},
}
items: {}
}

items_ai["custom-prompt-on-table"] = {
name: "Run custom prompt on table",
icon: "fa-table",
items: {
"custom-prompt-table-bard": {name: "Using bard", icon: "fa-b"},
}
items: {}
}


if(Zotero.ZeNotes.Prefs.getb("bard-api-key")!="")
{
items_ai["paraphrase-annotation"]["items"]["paraphrase-bard"] = {name: "Using bard", icon: "fa-b"};
items_ai["custom-prompt-on-cell"]["items"]["custom-prompt-cell-bard"] = {name: "Using bard", icon: "fa-b"};
items_ai["custom-prompt-on-row"]["items"]["custom-prompt-row-bard"] = {name: "Using bard", icon: "fa-b"};
items_ai["custom-prompt-on-table"]["items"]["custom-prompt-row-table"] = {name: "Using bard", icon: "fa-b"};
}

if(Zotero.ZeNotes.Prefs.getb("openai-api-key")!="")
{
items_ai["paraphrase-annotation"]["items"]["paraphrase-openai-gpt"] = {name: "Using Chat GPT", icon: "fa-g"};
items_ai["custom-prompt-on-cell"]["items"]["custom-prompt-cell-openai"] = {name: "Using Chat GPT", icon: "fa-g"};
items_ai["custom-prompt-on-row"]["items"]["custom-prompt-row-openai"] = {name: "Using Chat GPT", icon: "fa-g"};
items_ai["custom-prompt-on-table"]["items"]["custom-prompt-table-openai"] = {name: "Using Chat GPT", icon: "fa-g"};
}

items_ai["sep-ai-01"] = "---------";
}

Expand Down Expand Up @@ -439,10 +449,13 @@ Menus = {
else if(key.includes("custom-prompt-"))
{
var annotation = Zotero.Items.get(annotationid);
var target = "cell";
data = Table.celldata(td);

if(key.includes("-row"))
if(key.includes("cell"))
{
target = "cell";
data = Table.celldata(td);
}
else if(key.includes("-row"))
{
target = "row";
data = Table.rowdata(td.closest("tr"));
Expand Down Expand Up @@ -503,47 +516,104 @@ Menus = {
});
});
}
else if(key.includes("-openai"))
{
Zotero.ZeNotes.Ai.OpenAi.customprompt(JSON.stringify(data), target).then(r=>{
var model = Zotero.ZeNotes.Prefs.get("openai-model");
var table = AiUi.createdialog(annotation, currentcomment, r, "openai");
var div = document.createElement("div");
div.innerHTML = "<h2>Custom prompt</h2> "+customprompt+"<hr/>"+this.displayjson(data);
try {
TabbedDialog.open(table, div, function(){}, "Edit and choose a candidate [OpenAi: "+model+"]", "close");
}
catch(e)
{
alert(e);
}
}).catch(r=>{
var div = document.createElement("div");
div.innerHTML = "<h2>Custom prompt</h2> "+customprompt+"<hr/>"+this.displayjson(data);
var html = "";
if(Array.isArray(r))
{
html = r.join("<br/>");
}
else
{
html="-"+r;
}
TabbedDialog.open(html, div, function(){
});
});
}
}



else if(key=="paraphrase-bard")
else if(key.startsWith("paraphrase"))
{
if(!annotationkey)
{
alert("Annotation not found!");
return;
}

if(Zotero.ZeNotes.Prefs.getb("bard-api-key")=="")
{
alert("Please set API key first.\nGo to ZeNotes > Settings > General Settings > AI API settings");
return;
}

var annotation = Zotero.Items.get(annotationid);
var currentcomment = annotation.annotationComment;
if(currentcomment==null)
{
currentcomment = "";
}
Zotero.ZeNotes.Ai.Bard.paraphrase(annotation["annotationText"]).then(r=>{
var table = AiUi.createdialog(annotation, currentcomment, r, "bard");
var model = Zotero.ZeNotes.Prefs.get("bard-model");
Dialog.open(table, function(){}, "Edit and choose a paraphrase [Bard: "+model+"]", "close");
}).catch(r=>{
var html = "";
if(Array.isArray(r))

if(key.endsWith("-bard"))
{
if(Zotero.ZeNotes.Prefs.getb("bard-api-key")=="")
{
html = r.join("<br/>");
alert("Please set API key first.\nGo to ZeNotes > Settings > General Settings > AI API settings");
return;
}
else
Zotero.ZeNotes.Ai.Bard.paraphrase(annotation["annotationText"]).then(r=>{
var table = AiUi.createdialog(annotation, currentcomment, r, "bard");
var model = Zotero.ZeNotes.Prefs.get("bard-model");
Dialog.open(table, function(){}, "Edit and choose a paraphrase [Bard: "+model+"]", "close");
}).catch(r=>{
var html = "";
if(Array.isArray(r))
{
html = r.join("<br/>");
}
else
{
html="-"+r;
}
Dialog.open(html, function(){
});
});
}
else if(key.endsWith("-openai-gpt"))
{
if(Zotero.ZeNotes.Prefs.getb("openai-api-key")=="")
{
html="-"+r;
alert("Please set API key first.\nGo to ZeNotes > Settings > General Settings > AI API settings");
return;
}
Dialog.open(html, function(){

Zotero.ZeNotes.Ai.OpenAi.paraphrase(annotation["annotationText"]).then(r=>{
var table = AiUi.createdialog(annotation, currentcomment, r, "gpt");
var model = Zotero.ZeNotes.Prefs.get("openai-model");
Dialog.open(table, function(){}, "Edit and choose a paraphrase [OpenAi: "+model+"]", "close");
}).catch(r=>{
var html = "";
if(Array.isArray(r))
{
html = r.join("<br/>");
}
else
{
html="-"+r;
}
Dialog.open(html, function(){
});
});
});
}
}

else if(key=="showfile")
Expand Down
12 changes: 12 additions & 0 deletions content/settings/ai.xhtml
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,22 @@
<tr>
<td>Bard API key</td><td><input id="zn-bard-api-key" type="password" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'bard-api-key', 'encrypt');" style="width:100%;" placeholder="Enter your Bard API key"/></td><td style="width:1.1em;"> </td>
<td>Model</td><td> <select id="zn-bard-model" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'bard-model');" style="width:100%;" placeholder="Model">
<option value="">Choose model</option>
<option value="gemini-pro">Gemini Pro</option>
<option value="text-bison-001">Bison 1</option>
</select></td>
</tr>
<tr>
<td>OpenAi API key</td><td><input id="zn-openai-api-key" type="password" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'openai-api-key', 'encrypt');" style="width:100%;" placeholder="Enter your OpenAi API key"/></td><td style="width:1.1em;"> </td>
<td>Model</td><td> <select id="zn-openai-model" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'openai-model');" style="width:100%;" placeholder="Model">
<option value="">Choose model</option>
<option value="gpt-3.5-turbo">GPT 3.5 Turbo</option>
<option value="gpt-4">GPT 4</option>
</select></td>
</tr>
<tr>
<td>OpenAi max token</td><td colspan="4"><input id="zn-openai-max-token" type="text" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'openai-max-token');" style="width:100%;" placeholder="Enter max number of token used"/></td>
</tr>
<tr><td>Cell custom prompt</td><td colspan="4"><textarea id="zn-cell-custom-prompt" type="text" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'cell-custom-prompt');" style="width:100%;" placeholder="The annotation will be appended to your prompt."></textarea></td></tr>
<tr><td>Row summary prompt</td><td colspan="4"><textarea id="zn-row-custom-prompt" type="text" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'row-custom-prompt');" style="width:100%;" placeholder="The row annotations/notes data will be appended to your prompt."></textarea></td></tr>
<tr><td>Table summary prompt</td><td colspan="4"><textarea id="zn-table-custom-prompt" type="text" onchange="Zotero_Preferences.ZeNotes.setpreference(event, 'table-custom-prompt');" style="width:100%;" placeholder="The table annotations/notes data will be appended to your prompt."></textarea></td></tr>
Expand Down
7 changes: 6 additions & 1 deletion content/settings/preferences.js
Original file line number Diff line number Diff line change
Expand Up @@ -314,11 +314,16 @@ Zotero_Preferences.ZeNotes = {
Zotero_Preferences.ZeNotes.loadpreference("column-width", "zn-column-width");

Zotero_Preferences.ZeNotes.loadpreference("bard-api-key", "zn-bard-api-key", "encrypt");
Zotero_Preferences.ZeNotes.loadpreference("bard-model", "zn-bard-model");

Zotero_Preferences.ZeNotes.loadpreference("openai-api-key", "zn-openai-api-key", "encrypt");
Zotero_Preferences.ZeNotes.loadpreference("openai-model", "zn-openai-model");
Zotero_Preferences.ZeNotes.loadpreference("openai-max-token", "zn-openai-max-token");

Zotero_Preferences.ZeNotes.loadpreference("google-translate-key", "zn-google-translate-key", "encrypt");
Zotero_Preferences.ZeNotes.loadpreference("deepl-api-key", "zn-deepl-api-key", "encrypt");

Zotero_Preferences.ZeNotes.loadpreference("bard-model", "zn-bard-model");

Zotero_Preferences.ZeNotes.loadpreference("cell-custom-prompt", "zn-cell-custom-prompt");
Zotero_Preferences.ZeNotes.loadpreference("row-custom-prompt", "zn-row-custom-prompt");
Zotero_Preferences.ZeNotes.loadpreference("table-custom-prompt", "zn-table-custom-prompt");
Expand Down
2 changes: 1 addition & 1 deletion content/ui/tabbed-dialog.js
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ TabbedDialog = {

if(title!="")
{
this.dialog.title = title;
$("#main-tabbed-dialog").dialog( "option", "title", title);
}

if(buttons==null)
Expand Down
83 changes: 79 additions & 4 deletions core/ai.js
Original file line number Diff line number Diff line change
Expand Up @@ -93,7 +93,16 @@ Ai={
return Promise.resolve(["Error: "+e, JSON.stringify(data)]);
}
}

else if(mode.startsWith("gpt"))
{
try {
return Promise.resolve(data.choices.map(function(e){return e.message.content}));
}
catch(e)
{
return Promise.resolve(["Error: "+e, JSON.stringify(data)]);
}
}
}).catch(e=>{
return Promise.reject(["Error: "+e, JSON.stringify(data)]);
});
Expand All @@ -102,6 +111,7 @@ Ai={
cell: "Paraphrase and summarize 'Direct quotes'",
row: "Summarize the data below into a coherent literature review. Add source for each claim in the form (Author date). ",
table: "Summarize the data below into a coherent literature review. Add source for each claim in the form (Author date). ",
paraphrase: "Paraphrase the following passage.",
}
}

Expand Down Expand Up @@ -140,9 +150,7 @@ Ai.Bard = {
{
model = "gemini-pro";
}

var prompts = "Your are an academic. Paraphrase the following. "
return this.sendprompt(sentence, prompts, model)
return this.sendprompt(sentence, Ai.prompts["paraphrase"], model)
},

async customprompt(sentence, target)
Expand Down Expand Up @@ -264,4 +272,71 @@ Ai.DeepL = {
}
return Ai.request(url, options, "deepl-translate");
},
}

Ai.OpenAi = {
paraphrase(sentence){
var model = Zotero.ZeNotes.Prefs.get("openai-model");
return this.sendprompt(sentence, Ai.prompts["paraphrase"], model)
},

async customprompt(sentence, target)
{
var model = Zotero.ZeNotes.Prefs.get("openai-model");
var prompts = Zotero.ZeNotes.Prefs.get(target+"-custom-prompt");

if(prompts=="")
{
prompts = Ai.prompts[target];
}
return this.sendprompt(sentence, prompts, model)
},

async sendprompt(sentence, prompts, model) {
var apikey = Zotero.ZeNotes.Prefs.getb("openai-api-key");
var url = "https://api.openai.com/v1/chat/completions";
var maxtoken = 300;
try {
maxtoken = Zotero.ZeNotes.Prefs.get("openai-max-token");

if(maxtoken=="")
{
maxtoken = 300;
}
else if(isNaN(parseInt(maxtoken)))
{
alert("Please input Max token (a number) in settings > open ai max token.\nThe value 100 is used by default!\nCurrent value: "+maxtoken);
maxtoken = 300;
}
else
{
maxtoken = parseInt(maxtoken);
}

}catch(e){
maxtoken = 300;
}

var payload = {
model: model,
max_tokens: maxtoken,
messages: [
{role: "system", content: "You are an academic assistant."},
{role: "user", content: prompts},
{role: "user", content: sentence},
],
}

var options = {
method: 'POST',
headers: {
"Authorization": "Bearer "+apikey,
"Content-Type": "application/json",
},
body: JSON.stringify(payload),
}
return Ai.request(url, options, model);
},


}
Loading

0 comments on commit 3c91b71

Please sign in to comment.