aboutsummaryrefslogtreecommitdiff
path: root/brep/repository-details.cxx
blob: eb2885cbc77549ef01b56c152c910872993cc15f (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
// file      : brep/repository-details.cxx -*- C++ -*-
// copyright : Copyright (c) 2014-2015 Code Synthesis Ltd
// license   : MIT; see accompanying LICENSE file

#include <brep/repository-details>

#include <xml/serializer>

#include <odb/database.hxx>
#include <odb/transaction.hxx>

#include <web/xhtml>
#include <web/module>
#include <web/mime-url-encoding>

#include <brep/page>
#include <brep/types>
#include <brep/utility>
#include <brep/options>
#include <brep/package>
#include <brep/package-odb>
#include <brep/shared-database>

using namespace odb::core;
using namespace brep::cli;

void brep::repository_details::
init (scanner& s)
{
  MODULE_DIAG;

  options_ = make_shared<options::repository_details> (
    s, unknown_mode::fail, unknown_mode::fail);

  db_ = shared_database (options_->db_host (), options_->db_port ());
}

void brep::repository_details::
handle (request& rq, response& rs)
{
  using namespace web::xhtml;

  MODULE_DIAG;

  // The module options object is not changed after being created once per
  // server process.
  //
  static const dir_path& root (
    options_->root ().empty ()
    ? dir_path ("/")
    : options_->root ());

  // Make sure no parameters passed.
  //
  try
  {
    param_scanner s (rq.parameters ());
    params::repository_details (s, unknown_mode::fail, unknown_mode::fail);
  }
  catch (const unknown_argument& e)
  {
    throw invalid_request (400, e.what ());
  }

  static const string title ("About");
  xml::serializer s (rs.content (), title);

  s << HTML
    <<   HEAD
    <<     TITLE << title << ~TITLE
    <<     CSS_LINKS (path ("repository-details.css"), root)
    <<   ~HEAD
    <<   BODY
    <<     DIV_HEADER (root)
    <<     DIV(ID="content");

  transaction t (db_->begin ());

  using query = query<repository>;

  for (const auto& r:
         db_->query<repository> (
           query::internal + "ORDER BY" + query::priority))
  {
    //@@ Feels like a lot of trouble (e.g., id_attribute()) for very
    //   dubious value. A link to the package search page just for
    //   this repository would probably be more useful.
    //
    string id (html_id (r.name));
    s << H1(ID=id)
      <<   A(HREF="#" + web::mime_url_encode (id)) << r.display_name << ~A
      << ~H1;

    if (r.summary)
      s << H2 << *r.summary << ~H2;

    if (r.description)
      s << P_DESCRIPTION (*r.description);

    if (r.email)
      s << P << A(HREF="mailto:" + *r.email) << *r.email << ~A << ~P;
  }

  t.commit ();

  s <<     ~DIV
    <<   ~BODY
    << ~HTML;
}