implement adding friends

This commit is contained in:
2019-07-03 22:47:12 +02:00
parent 2e563b724a
commit efce6a6543
8 changed files with 231 additions and 68 deletions

View File

@@ -1,9 +1,10 @@
#include <ncdc/cmds.h>
ncdc_commands_t cmds[] = {
{ L"friends", ncdc_cmd_friends },
{ L"login", ncdc_cmd_login },
{ L"quit", ncdc_cmd_quit },
{ L"/friend", ncdc_cmd_friends },
{ L"/friends", ncdc_cmd_friends },
{ L"/login", ncdc_cmd_login },
{ L"/quit", ncdc_cmd_quit },
{ NULL, NULL }
};
@@ -36,7 +37,6 @@ static void *async_dispatcher(void *arg)
/* end of working orders
*/
pthread_mutex_unlock(&mtx);
printf("got exit\n");
return NULL;
} else {
/* call the handler
@@ -92,15 +92,17 @@ bool ncdc_dispatch_deinit(void)
bool ncdc_dispatch(ncdc_mainwindow_t n, wchar_t const *s)
{
wchar_t **tokens = NULL;
size_t i = 0;
size_t i = 0, tokenlen = 0;
ncdc_commands_t *it = NULL;
queue_item *item = NULL;
tokens = w_tokenise(s);
return_if_true(tokens == NULL, false);
tokenlen = wcslen(tokens[0]);
for (i = 0; cmds[i].name != NULL; i++) {
if (wcscmp(cmds[i].name, tokens[0]) == 0) {
if (wcsncmp(cmds[i].name, tokens[0], tokenlen) == 0) {
it = cmds+i;
break;
}

View File

@@ -6,6 +6,7 @@ ncdc_cmd_friends_list(ncdc_mainwindow_t n, size_t ac, wchar_t **av)
{
bool ret = false;
size_t i = 0;
wchar_t c = ' ';
ret = dc_api_get_friends(api, current_account);
if (!ret) {
@@ -16,27 +17,67 @@ ncdc_cmd_friends_list(ncdc_mainwindow_t n, size_t ac, wchar_t **av)
LOG(n, L"/FRIENDS list");
for (i = 0; i < dc_account_friends_size(current_account); i++) {
dc_account_t acc = dc_account_nthfriend(current_account, i);
LOG(n, L" %s", dc_account_full_username(acc));
switch (dc_account_friend_state(acc)) {
case FRIEND_STATE_PENDING: c = 'P'; break;
default: c = ' '; break;
}
LOG(n, L"%lc %s", c, dc_account_full_username(acc));
}
LOG(n, L"End of /FRIENDS list");
return true;
}
bool ncdc_cmd_friends(ncdc_mainwindow_t n, size_t ac, wchar_t **av)
static bool
ncdc_cmd_friends_add(ncdc_mainwindow_t n, size_t ac, wchar_t **av)
{
wchar_t *subcmd = NULL;
char *name = NULL;
dc_account_t friend = NULL;
bool ret = false;
if (ac <= 1) {
return false;
}
name = w_convert(av[1]);
return_if_true(name == NULL, false);
friend = dc_account_from_fullid(name);
if (friend == NULL) {
LOG(n, L"friends: add: invalid username given, use the full ID");
goto cleanup;
}
if (!dc_api_add_friend(api, current_account, friend)) {
LOG(n, L"friends: add: failed to add friend, Vulkan would be sad");
goto cleanup;
}
LOG(n, L"friends: add: request for friendship sent");
ret = true;
cleanup:
dc_unref(friend);
free(name);
return ret;
}
bool ncdc_cmd_friends(ncdc_mainwindow_t n, size_t ac, wchar_t **av)
{
wchar_t *subcmd = NULL;
if (current_account == NULL ||
!dc_account_has_token(current_account)) {
LOG(n, L"friends: not logged in");
return false;
}
if (ac <= 1) {
return ncdc_cmd_friends_list(n, ac, av);
}
subcmd = av[1];
--ac;
@@ -44,6 +85,8 @@ bool ncdc_cmd_friends(ncdc_mainwindow_t n, size_t ac, wchar_t **av)
if (wcscmp(subcmd, L"list") == 0) {
return ncdc_cmd_friends_list(n, ac, av);
} else if (wcscmp(subcmd, L"add") == 0) {
return ncdc_cmd_friends_add(n, ac, av);
} else {
return false;
}

View File

@@ -99,12 +99,12 @@ ncdc_mainwindow_callback(ncdc_input_t i, wchar_t const *s,
{
ncdc_mainwindow_t mainwin = (ncdc_mainwindow_t)arg;
if (s[0] == '/') {
if (s != NULL && s[0] == '/') {
if (s[1] == '\0') {
return false;
}
return ncdc_dispatch(mainwin, s+1);
return ncdc_dispatch(mainwin, s);
}
return false;

View File

@@ -33,11 +33,11 @@ int aswprintf(wchar_t **buffer, wchar_t const *fmt, ...)
return sz;
}
wchar_t* wcsndup(const wchar_t* string, size_t maxlen)
wchar_t* wcsndup(wchar_t const* string, size_t maxlen)
{
size_t n = wcsnlen(string, maxlen) + 1;
wchar_t* r = calloc(n, sizeof(wchar_t));
return r == NULL ? NULL : wmemcpy(r, string, n);
wchar_t* r = calloc(maxlen+1, sizeof(wchar_t));
return_if_true(r == NULL, NULL);
return wmemcpy(r, string, maxlen);
}
size_t w_strlenv(wchar_t **s)
@@ -61,28 +61,56 @@ void w_strfreev(wchar_t **s)
free(s);
}
wchar_t **w_tokenise(wchar_t const *w)
wchar_t **w_tokenise(wchar_t const *str)
{
wchar_t const *p = NULL, *start_of_word = NULL;
wint_t c;
GPtrArray *array = g_ptr_array_new();
wchar_t const *item = w;
wchar_t *dup = NULL;
size_t len = 0, origlen = 0;
enum states { DULL, IN_WORD, IN_STRING } state = DULL;
while ((dup = w_next_tok(item)) != NULL) {
len = origlen = wcslen(dup);
for (p = str; *p != '\0'; p++) {
c = (wint_t) *p;
switch (state) {
case DULL:
{
if (iswspace(c)) {
continue;
}
if (c == '"') {
state = IN_STRING;
start_of_word = p + 1;
continue;
}
state = IN_WORD;
start_of_word = p;
} continue;
if (*dup == '"') {
memmove(dup, dup+1, sizeof(wchar_t)*(len-1));
--len;
case IN_STRING:
{
if (c == '"') {
size_t len = (p - 2 - start_of_word);
wchar_t *s = wcsndup(start_of_word, len);
g_ptr_array_add(array, s);
state = DULL;
}
} continue;
case IN_WORD:
{
if (iswspace(c)) {
size_t len = (p - start_of_word);
wchar_t *s = wcsndup(start_of_word, len);
g_ptr_array_add(array, s);
state = DULL;
}
} continue;
}
}
if (len > 0 && dup[len-1] == '"') {
dup[len-1] = '\0';
--len;
}
g_ptr_array_add(array, dup);
item += origlen;
if (state != DULL) {
size_t len = (p - start_of_word);
wchar_t *s = wcsndup(start_of_word, len);
g_ptr_array_add(array, s);
}
g_ptr_array_add(array, NULL);
@@ -103,40 +131,3 @@ char *w_convert(wchar_t const *w)
wcstombs(ptr, w, sz);
return ptr;
}
wchar_t *w_next_tok(wchar_t const *w)
{
bool quotes = false;
wchar_t const *start = NULL;
/* skip first white spaces if there are any
*/
for (; *w != '\0' && iswspace(*w); w++)
;
if (*w == '\0') {
return NULL;
}
start = w;
quotes = (*w == '"');
do {
if (iswspace(*w) && !quotes) {
--w;
break;
}
if (*w == '"' && *(w-1) != '\\' && quotes) {
break;
}
if (*w == '\0') {
break;
}
++w;
} while (1);
return wcsndup(start, (w - start));
}