aboutsummaryrefslogtreecommitdiff
path: root/page.c
diff options
context:
space:
mode:
Diffstat (limited to 'page.c')
-rw-r--r--page.c360
1 files changed, 359 insertions, 1 deletions
diff --git a/page.c b/page.c
index 3139184..3268b9a 100644
--- a/page.c
+++ b/page.c
@@ -45,6 +45,55 @@
" <input type=\"submit\" value=\"Submit\">\n" \
" </form>\n"
#define MAXSIZEFMT "18446744073709551615.0 XiB"
+#define RM_FORM_ID "rm"
+
+static int prepare_rm_checkbox(struct html_node *const n,
+ const struct stat *const sb, const char *const name)
+{
+ int ret = -1;
+ const char *const sep = S_ISDIR(sb->st_mode) ? "/" : "";
+ struct html_node *input;
+ struct dynstr d;
+
+ dynstr_init(&d);
+
+ if (dynstr_append(&d, "%s%s", name, sep))
+ {
+ fprintf(stderr, "%s: dynstr_append failed\n", __func__);
+ goto end;
+ }
+ else if (!(input = html_node_add_child(n, "input")))
+ {
+ fprintf(stderr, "%s: html_node_add_child input failed\n", __func__);
+ goto end;
+ }
+ else if (html_node_add_attr(input, "type", "checkbox"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr type failed\n", __func__);
+ goto end;
+ }
+ else if (html_node_add_attr(input, "form", RM_FORM_ID))
+ {
+ fprintf(stderr, "%s: html_node_add_attr form failed\n", __func__);
+ goto end;
+ }
+ else if (html_node_add_attr(input, "name", "path"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr name failed\n", __func__);
+ goto end;
+ }
+ else if (html_node_add_attr(input, "value", d.str))
+ {
+ fprintf(stderr, "%s: html_node_add_attr value failed\n", __func__);
+ goto end;
+ }
+
+ ret = 0;
+
+end:
+ dynstr_free(&d);
+ return ret;
+}
static int prepare_name(struct html_node *const n, struct stat *const sb,
const char *const dir, const char *const name)
@@ -287,7 +336,7 @@ static int add_element(struct html_node *const n, const char *const dir,
const char *const res, const char *const name)
{
int ret = -1;
- enum {NAME, SIZE, DATE, SHARE, PREVIEW, COLUMNS};
+ enum {RM_CHECKBOX, NAME, SIZE, DATE, SHARE, PREVIEW, COLUMNS};
struct html_node *tr, *td[COLUMNS];
struct dynstr path;
const char *const sep = res[strlen(res) - 1] != '/' ? "/" : "";
@@ -321,6 +370,12 @@ static int add_element(struct html_node *const n, const char *const dir,
__func__, path.str, strerror(errno));
goto end;
}
+ else if (strcmp(name, "..")
+ && prepare_rm_checkbox(td[RM_CHECKBOX], &sb, name))
+ {
+ fprintf(stderr, "%s: prepare_rm_checkbox failed\n", __func__);
+ goto end;
+ }
else if (prepare_name(td[NAME], &sb, dir, name))
{
fprintf(stderr, "%s: prepare_name failed\n", __func__);
@@ -618,6 +673,80 @@ static int prepare_mkdir_form(struct html_node *const n, const char *const dir)
return 0;
}
+static int prepare_rm_form(struct html_node *const n, const char *const dir)
+{
+ struct html_node *div, *form, *hidden, *submit;
+
+ if (!(div = html_node_add_child(n, "div")))
+ {
+ fprintf(stderr, "%s: html_node_add_child div failed\n", __func__);
+ return -1;
+ }
+ else if (!(form = html_node_add_child(div, "form")))
+ {
+ fprintf(stderr, "%s: html_node_add_child form failed\n", __func__);
+ return -1;
+ }
+ else if (!(hidden = html_node_add_child(form, "input")))
+ {
+ fprintf(stderr, "%s: html_node_add_child hidden failed\n", __func__);
+ return -1;
+ }
+ else if (!(submit = html_node_add_child(form, "input")))
+ {
+ fprintf(stderr, "%s: html_node_add_child submit failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(div, "class", "userform"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr div failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(form, "id", RM_FORM_ID))
+ {
+ fprintf(stderr, "%s: html_node_add_attr id failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(form, "method", "post"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr method failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(form, "action", "/confirm/rm"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr method failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(hidden, "type", "hidden"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr hidden failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(hidden, "name", "dir"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr name failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(hidden, "value", dir))
+ {
+ fprintf(stderr, "%s: html_node_add_attr value failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(submit, "type", "submit"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr submit failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(submit, "value", "Remove selected files"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr submit value failed\n",
+ __func__);
+ return -1;
+ }
+
+ return 0;
+}
+
static int prepare_quota_form(struct html_node *const n,
const struct page_quota *const q)
{
@@ -957,6 +1086,11 @@ static struct html_node *resource_layout(const char *const dir,
fprintf(stderr, "%s: prepare_upload_form failed\n", __func__);
goto end;
}
+ else if (prepare_rm_form(body, fdir))
+ {
+ fprintf(stderr, "%s: prepare_upload_form failed\n", __func__);
+ goto end;
+ }
else if (q && prepare_quota_form(body, q))
{
fprintf(stderr, "%s: prepare_quota_form failed\n", __func__);
@@ -1782,3 +1916,227 @@ end:
return ret;
}
+
+static int append_rm_items(struct html_node *const n,
+ const struct page_rm *const rm)
+{
+ struct html_node *div, *form, *table, *hidden, *submit;
+
+ if (!(table = html_node_add_child(n, "table")))
+ {
+ fprintf(stderr, "%s: html_node_add_child table failed\n", __func__);
+ return -1;
+ }
+ else if (!(div = html_node_add_child(n, "div")))
+ {
+ fprintf(stderr, "%s: html_node_add_child div failed\n", __func__);
+ return -1;
+ }
+ else if (!(form = html_node_add_child(div, "form")))
+ {
+ fprintf(stderr, "%s: html_node_add_child form failed\n", __func__);
+ return -1;
+ }
+ else if (!(hidden = html_node_add_child(form, "input")))
+ {
+ fprintf(stderr, "%s: html_node_add_child hidden failed\n", __func__);
+ return -1;
+ }
+ else if (!(submit = html_node_add_child(form, "input")))
+ {
+ fprintf(stderr, "%s: html_node_add_child submit failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(form, "method", "post"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr method failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(form, "action", "/rm"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr action failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(div, "class", "userform"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr class failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(hidden, "type", "hidden"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr hidden type failed\n",
+ __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(hidden, "name", "dir"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr hidden name failed\n",
+ __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(hidden, "value", rm->dir))
+ {
+ fprintf(stderr, "%s: html_node_add_attr hidden value failed\n",
+ __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(submit, "type", "submit"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr submit type failed\n",
+ __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(submit, "value", "Confirm"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr submit value failed\n",
+ __func__);
+ return -1;
+ }
+
+ for (size_t i = 0; i < rm->n; i++)
+ {
+ const char *const item = rm->items[i];
+ struct html_node *const tr = html_node_add_child(table, "tr"),
+ *const path = html_node_add_child(form, "input"), *td;
+
+ if (!tr)
+ {
+ fprintf(stderr, "%s: html_node_add_child tr failed\n", __func__);
+ return -1;
+ }
+ else if (!path)
+ {
+ fprintf(stderr, "%s: html_node_add_child path failed\n", __func__);
+ return -1;
+ }
+ else if (!(td = html_node_add_child(tr, "td")))
+ {
+ fprintf(stderr, "%s: html_node_add_child td failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_set_value(td, item))
+ {
+ fprintf(stderr, "%s: html_node_set_value td failed\n", __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(path, "type", "hidden"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr path type failed\n",
+ __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(path, "name", "path"))
+ {
+ fprintf(stderr, "%s: html_node_add_attr path name failed\n",
+ __func__);
+ return -1;
+ }
+ else if (html_node_add_attr(path, "value", item))
+ {
+ fprintf(stderr, "%s: html_node_add_attr path value failed\n",
+ __func__);
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+int page_rm(struct http_response *r, const struct page_rm *const rm)
+{
+ int ret = -1;
+ struct dynstr out;
+ struct html_node *const html = html_node_alloc("html"),
+ *p, *p2, *head, *body;
+ static const char question[] = "Are you sure to remove the "
+ "following files and/or directories? Remember that removing a "
+ "directory will remove all of the files and directories inside it.",
+ reminder[] = "This action cannot be undone.";
+
+ dynstr_init(&out);
+
+ if (!html)
+ {
+ fprintf(stderr, "%s: html_node_alloc failed\n", __func__);
+ goto end;
+ }
+ else if (!(head = html_node_add_child(html, "head")))
+ {
+ fprintf(stderr, "%s: html_node_add_child head failed\n", __func__);
+ goto end;
+ }
+ else if (!(body = html_node_add_child(html, "body")))
+ {
+ fprintf(stderr, "%s: html_node_add_child body failed\n", __func__);
+ goto end;
+ }
+ else if (!(p = html_node_add_child(body, "p")))
+ {
+ fprintf(stderr, "%s: html_node_add_child p failed\n", __func__);
+ goto end;
+ }
+ else if (!(p2 = html_node_add_child(body, "p")))
+ {
+ fprintf(stderr, "%s: html_node_add_child p2 failed\n", __func__);
+ goto end;
+ }
+ else if (common_head(head, NULL))
+ {
+ fprintf(stderr, "%s: common_head failed\n", __func__);
+ goto end;
+ }
+ else if (html_node_set_value(p, question))
+ {
+ fprintf(stderr, "%s: html_node_set_value question failed\n", __func__);
+ goto end;
+ }
+ else if (html_node_set_value(p2, reminder))
+ {
+ fprintf(stderr, "%s: html_node_set_value reminder failed\n", __func__);
+ goto end;
+ }
+ else if (append_rm_items(body, rm))
+ {
+ fprintf(stderr, "%s: append_rm_items failed\n", __func__);
+ goto end;
+ }
+ else if (prepare_footer(body))
+ {
+ fprintf(stderr, "%s: prepare_footer failed\n", __func__);
+ goto end;
+ }
+ else if (dynstr_append(&out, DOCTYPE_TAG))
+ {
+ fprintf(stderr, "%s: dynstr_append out failed\n", __func__);
+ goto end;
+ }
+ else if (html_serialize(html, &out))
+ {
+ fprintf(stderr, "%s: html_serialize failed\n", __func__);
+ goto end;
+ }
+
+ *r = (const struct http_response)
+ {
+ .status = HTTP_STATUS_OK,
+ .buf.rw = out.str,
+ .n = out.len,
+ .free = free
+ };
+
+ if (http_response_add_header(r, "Content-Type", "text/html"))
+ {
+ fprintf(stderr, "%s: http_response_add_header failed\n", __func__);
+ goto end;
+ }
+
+ ret = 0;
+
+end:
+ html_node_free(html);
+
+ if (ret)
+ dynstr_free(&out);
+
+ return ret;
+}