1
0
mirror of https://github.com/bitwarden/web synced 2026-01-16 23:43:13 +00:00

Update 2017-05-03T14:30:05.647Z

This commit is contained in:
Kyle Spearrin
2017-05-03 10:30:11 -04:00
parent 2d7f83905b
commit db7ff13f2e
52 changed files with 5931 additions and 1296 deletions

View File

@@ -35,7 +35,15 @@
</div>
<hr />
<ul>
<li><a ui-sref="frontend.register">Create a new account</a></li>
<li><a ui-sref="frontend.passwordHint">Get master password hint</a></li>
<li>
<a ui-sref="frontend.register({returnState: state.params.returnState, email: state.params.email})">
Create a new account
</a>
</li>
<li>
<a ui-sref="frontend.passwordHint">
Get master password hint
</a>
</li>
</ul>
</form>

View File

@@ -0,0 +1,32 @@
<div class="login-box">
<div class="login-logo">
<i class="fa fa-shield"></i> <b>bit</b>warden
</div>
<div class="login-box-body">
<div ng-show="loading">
Loading...
</div>
<div ng-show="accepting">
Accepting invitation...
</div>
<div ng-show="!loading && !accepting">
<p class="login-box-msg">Join {{state.params.organizationName}}</p>
<p class="text-center"><strong>{{state.params.email}}</strong></p>
<p>
You've been invited to join the organization listed above.
To accept the invitation, you need to log in or create a new bitwarden account.
</p>
<hr />
<div class="row">
<div class="col-sm-6">
<a ui-sref="frontend.login.info({returnState: state, email: state.params.email})"
class="btn btn-primary btn-block btn-flat">Log In</a>
</div>
<div class="col-sm-6">
<a ui-sref="frontend.register({returnState: state, email: state.params.email})"
class="btn btn-primary btn-block btn-flat">Create Account</a>
</div>
</div>
</div>
</div>
</div>

View File

@@ -9,10 +9,14 @@
<h4>Account Created!</h4>
<p>You may now log in to your new account.</p>
</div>
<a ui-sref="frontend.login.info">Ready to log in?</a>
<a ui-sref="frontend.login.info({returnState: returnState, email: model.email})">Ready to log in?</a>
</div>
<form name="registerForm" ng-submit="registerForm.$valid && register(registerForm)" ng-show="!success"
api-form="registerPromise">
<div class="callout callout-default" ng-show="createOrg">
<h4>Create Organization, Step 1</h4>
<p>Before creating your organization, you first need to create a free personal account.</p>
</div>
<div class="callout callout-danger validation-errors" ng-show="registerForm.$errors">
<h4>Errors have occured</h4>
<ul>
@@ -22,7 +26,7 @@
<div class="form-group has-feedback" show-errors>
<label for="email" class="sr-only">Email</label>
<input type="email" id="email" name="Email" class="form-control" placeholder="Email" ng-model="model.email"
required api-field />
ng-readonly="readOnlyEmail" required api-field />
<span class="fa fa-envelope form-control-feedback"></span>
<p class="help-block">You'll use your email address to log in.</p>
</div>
@@ -60,7 +64,7 @@
</div>
<div class="row">
<div class="col-xs-7">
<a ui-sref="frontend.login.info">Already have an account?</a>
<a ui-sref="frontend.login.info({returnState: returnState})">Already have an account?</a>
</div>
<div class="col-xs-5">
<button type="submit" class="btn btn-primary btn-block btn-flat" ng-disabled="registerForm.$loading">

View File

@@ -0,0 +1,161 @@
<section class="content-header">
<h1>
Billing
<small>manage your payments</small>
</h1>
</section>
<section class="content">
<div class="callout callout-warning" ng-if="subscription && subscription.cancelled">
<h4><i class="fa fa-warning"></i> Cancelled</h4>
The subscription to this organization has been canceled.
</div>
<div class="callout callout-warning" ng-if="subscription && subscription.markedForCancel">
<h4><i class="fa fa-warning"></i> Pending Cancellation</h4>
<p>
The subscription to this organization has been marked for cancellation at the end of the
current billing period.
</p>
<button type="button" class="btn btn-default btn-flat" ng-click="reinstate()">
Reinstate Plan
</button>
</div>
<div class="box">
<div class="box-header with-border">
<h3 class="box-title">Plan</h3>
</div>
<div class="box-body">
<div class="row">
<div class="col-sm-6">
<dl>
<dt>Name</dt>
<dd>{{plan.name || '-'}}</dd>
<dt>Total Seats</dt>
<dd>{{plan.seats || '-'}}</dd>
</dl>
</div>
<div class="col-sm-6">
<dl>
<dt>Status</dt>
<dd style="text-transform: capitalize;">{{(subscription && subscription.status) || '-'}}</dd>
<dt>Next Charge</dt>
<dd>{{nextInvoice ? ((nextInvoice.date | date: format: mediumDate) + ', ' + (nextInvoice.amount | currency:'$')) : '-'}}</dd>
</dl>
</div>
</div>
<div class="row" ng-if="!noSubscription">
<div class="col-md-6">
<strong>Details</strong>
<div ng-show="loading">
Loading...
</div>
<div class="table-responsive" style="margin: 0;" ng-show="!loading">
<table class="table" style="margin: 0;">
<tbody>
<tr ng-repeat="item in subscription.items">
<td>
{{item.name}} {{item.qty > 1 ? '&times;' + item.qty : ''}}
@ {{item.amount | currency:'$'}} /{{item.interval}}
</td>
<td class="text-right">{{(item.qty * item.amount) | currency:'$'}} /{{item.interval}}</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
<div class="box-footer">
<button type="button" class="btn btn-default btn-flat" ng-click="changePlan()">
Change Plan
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="cancel()"
ng-if="!noSubscription && !subscription.cancelled && !subscription.markedForCancel">
Cancel Plan
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="reinstate()"
ng-if="!noSubscription && subscription.markedForCancel">
Reinstate Plan
</button>
</div>
</div>
<div class="box">
<div class="box-header with-border">
<h3 class="box-title">User Seats</h3>
</div>
<div class="box-body">
<div ng-show="loading">
Loading...
</div>
<div ng-show="!loading">
You plan currently has a total of <b>{{plan.seats}}</b> seats.
</div>
</div>
<div class="box-footer" ng-if="!noSubscription">
<button type="button" class="btn btn-default btn-flat" ng-click="adjustSeats(true)">
Add Seats
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="adjustSeats(false)">
Remove Seats
</button>
</div>
</div>
<div class="box">
<div class="box-header with-border">
<h3 class="box-title">Payment Method</h3>
</div>
<div class="box-body">
<div ng-show="loading">
Loading...
</div>
<div ng-show="!loading && !paymentSource">
<i class="fa fa-credit-card"></i> No payment method on file.
</div>
<div ng-show="!loading && paymentSource">
<i class="fa" ng-class="{'fa-credit-card': paymentSource.type === 0,
'fa-university': paymentSource.type === 1}"></i>
{{paymentSource.description}}
</div>
</div>
<div class="box-footer">
<button type="button" class="btn btn-default btn-flat" ng-click="changePayment()">
{{ paymentSource ? 'Change Payment Method' : 'Add Payment Method' }}
</button>
</div>
</div>
<div class="box">
<div class="box-header with-border">
<h3 class="box-title">Charges</h3>
</div>
<div class="box-body">
<div ng-show="loading">
Loading...
</div>
<div ng-show="!loading && !charges.length">
No charges.
</div>
<div class="table-responsive" ng-show="charges.length">
<table class="table">
<tbody>
<tr ng-repeat="charge in charges">
<td style="width: 200px">
{{charge.date | date: format: mediumDate}}
</td>
<td>
{{charge.paymentSource}}
</td>
<td style="width: 150px; text-transform: capitalize;">
{{charge.status}}
</td>
<td class="text-right" style="width: 150px;">
{{charge.amount | currency:'$'}}
</td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="box-footer">
Note: Any charges will appears on your credit card statement as <b>BITWARDEN</b>.
</div>
</div>
</section>

View File

@@ -0,0 +1,46 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">
<i class="fa fa-users"></i>
{{add ? 'Add Seats' : 'Remove Seats'}}
</h4>
</div>
<form name="form" ng-submit="form.$valid && submit()" api-form="submitPromise">
<div class="modal-body">
<div class="callout callout-default" ng-show="add">
<h4><i class="fa fa-dollar"></i> Note About Charges</h4>
<p>
Adding seats to your plan will result in adjustments to your billing totals and immediately charge your
payment method on file. The first charge will be prorated for the remainder of the current billing cycle.
</p>
</div>
<div class="callout callout-default" ng-show="!add">
<h4><i class="fa fa-dollar"></i> Note About Charges</h4>
<p>
Removing seats will result in adjustments to your billing totals that will be prorated as credits
to your next billing charge.
</p>
</div>
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<div class="row">
<div class="col-md-6">
<div class="form-group">
<label for="seats">{{add ? 'Seats To Add' : 'Seats To Remove'}}</label>
<input type="number" id="seats" name="SeatAdjustment" ng-model="seatAdjustment" class="form-control"
required min="0" />
</div>
</div>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Submit
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,364 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">
<i class="fa fa-credit-card"></i>
{{existingPaymentMethod ? 'Change Payment Method' : 'Add Payment Method'}}
</h4>
</div>
<form name="form" ng-submit="form.$valid && submit()" api-form="submitPromise">
<div class="modal-body">
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<div class="row">
<div class="col-md-6">
<div class="form-group" show-errors>
<label for="card_number">Card Number</label>
<input type="text" id="card_number" name="card_number" ng-model="card.number"
class="form-control" cc-number required api-field />
</div>
</div>
</div>
<ul class="list-inline">
<li><div class="cc visa"></div></li>
<li><div class="cc mastercard"></div></li>
<li><div class="cc amex"></div></li>
<li><div class="cc discover"></div></li>
<li><div class="cc diners"></div></li>
<li><div class="cc jcb"></div></li>
</ul>
<div class="row">
<div class="col-sm-4">
<div class="form-group" show-errors>
<label for="exp_month">Expiration Month</label>
<select id="exp_month" class="form-control" ng-model="card.exp_month" required cc-exp-month
name="exp_month" api-field>
<option value="">-- Select --</option>
<option value="01">01 - January</option>
<option value="02">02 - February</option>
<option value="03">03 - March</option>
<option value="04">04 - April</option>
<option value="05">05 - May</option>
<option value="06">06 - June</option>
<option value="07">07 - July</option>
<option value="08">08 - August</option>
<option value="09">09 - September</option>
<option value="10">10 - October</option>
<option value="11">11 - November</option>
<option value="12">12 - December</option>
</select>
</div>
</div>
<div class="col-sm-4">
<div class="form-group" show-errors>
<label for="exp_year">Expiration Year</label>
<select id="exp_year" class="form-control" ng-model="card.exp_year" required cc-exp-year
name="exp_year" api-field>
<option value="">-- Select --</option>
<option value="17">2017</option>
<option value="18">2018</option>
<option value="19">2019</option>
<option value="20">2020</option>
<option value="21">2021</option>
<option value="22">2022</option>
<option value="23">2023</option>
<option value="24">2024</option>
<option value="25">2025</option>
<option value="26">2026</option>
</select>
</div>
</div>
<div class="col-sm-4">
<div class="form-group" show-errors>
<label for="cvc">
CVC
<a href="https://www.cvvnumber.com/cvv.html" target="_blank" title="What is this?"
rel="noopener noreferrer">
<i class="fa fa-question-circle"></i>
</a>
</label>
<input type="text" id="cvc" ng-model="card.cvc" class="form-control" name="cvc"
cc-type="number.$ccType" cc-cvc required api-field />
</div>
</div>
</div>
<div class="row">
<div class="col-sm-6">
<div class="form-group" show-errors>
<label for="address_country">Country</label>
<select id="address_country" class="form-control" ng-model="card.address_country"
required name="address_country" api-field>
<option value="">-- Select --</option>
<option value="US">United States</option>
<option value="CN">China</option>
<option value="FR">France</option>
<option value="DE">Germany</option>
<option value="CA">Canada</option>
<option value="GB">United Kingdom</option>
<option value="AU">Australia</option>
<option value="IN">India</option>
<option value="-" disabled></option>
<option value="AF">Afghanistan</option>
<option value="AX">Åland Islands</option>
<option value="AL">Albania</option>
<option value="DZ">Algeria</option>
<option value="AS">American Samoa</option>
<option value="AD">Andorra</option>
<option value="AO">Angola</option>
<option value="AI">Anguilla</option>
<option value="AQ">Antarctica</option>
<option value="AG">Antigua and Barbuda</option>
<option value="AR">Argentina</option>
<option value="AM">Armenia</option>
<option value="AW">Aruba</option>
<option value="AT">Austria</option>
<option value="AZ">Azerbaijan</option>
<option value="BS">Bahamas</option>
<option value="BH">Bahrain</option>
<option value="BD">Bangladesh</option>
<option value="BB">Barbados</option>
<option value="BY">Belarus</option>
<option value="BE">Belgium</option>
<option value="BZ">Belize</option>
<option value="BJ">Benin</option>
<option value="BM">Bermuda</option>
<option value="BT">Bhutan</option>
<option value="BO">Bolivia, Plurinational State of</option>
<option value="BQ">Bonaire, Sint Eustatius and Saba</option>
<option value="BA">Bosnia and Herzegovina</option>
<option value="BW">Botswana</option>
<option value="BV">Bouvet Island</option>
<option value="BR">Brazil</option>
<option value="IO">British Indian Ocean Territory</option>
<option value="BN">Brunei Darussalam</option>
<option value="BG">Bulgaria</option>
<option value="BF">Burkina Faso</option>
<option value="BI">Burundi</option>
<option value="KH">Cambodia</option>
<option value="CM">Cameroon</option>
<option value="CV">Cape Verde</option>
<option value="KY">Cayman Islands</option>
<option value="CF">Central African Republic</option>
<option value="TD">Chad</option>
<option value="CL">Chile</option>
<option value="CX">Christmas Island</option>
<option value="CC">Cocos (Keeling) Islands</option>
<option value="CO">Colombia</option>
<option value="KM">Comoros</option>
<option value="CG">Congo</option>
<option value="CD">Congo, the Democratic Republic of the</option>
<option value="CK">Cook Islands</option>
<option value="CR">Costa Rica</option>
<option value="CI">Côte d'Ivoire</option>
<option value="HR">Croatia</option>
<option value="CU">Cuba</option>
<option value="CW">Curaçao</option>
<option value="CY">Cyprus</option>
<option value="CZ">Czech Republic</option>
<option value="DK">Denmark</option>
<option value="DJ">Djibouti</option>
<option value="DM">Dominica</option>
<option value="DO">Dominican Republic</option>
<option value="EC">Ecuador</option>
<option value="EG">Egypt</option>
<option value="SV">El Salvador</option>
<option value="GQ">Equatorial Guinea</option>
<option value="ER">Eritrea</option>
<option value="EE">Estonia</option>
<option value="ET">Ethiopia</option>
<option value="FK">Falkland Islands (Malvinas)</option>
<option value="FO">Faroe Islands</option>
<option value="FJ">Fiji</option>
<option value="FI">Finland</option>
<option value="GF">French Guiana</option>
<option value="PF">French Polynesia</option>
<option value="TF">French Southern Territories</option>
<option value="GA">Gabon</option>
<option value="GM">Gambia</option>
<option value="GE">Georgia</option>
<option value="GH">Ghana</option>
<option value="GI">Gibraltar</option>
<option value="GR">Greece</option>
<option value="GL">Greenland</option>
<option value="GD">Grenada</option>
<option value="GP">Guadeloupe</option>
<option value="GU">Guam</option>
<option value="GT">Guatemala</option>
<option value="GG">Guernsey</option>
<option value="GN">Guinea</option>
<option value="GW">Guinea-Bissau</option>
<option value="GY">Guyana</option>
<option value="HT">Haiti</option>
<option value="HM">Heard Island and McDonald Islands</option>
<option value="VA">Holy See (Vatican City State)</option>
<option value="HN">Honduras</option>
<option value="HK">Hong Kong</option>
<option value="HU">Hungary</option>
<option value="IS">Iceland</option>
<option value="ID">Indonesia</option>
<option value="IR">Iran, Islamic Republic of</option>
<option value="IQ">Iraq</option>
<option value="IE">Ireland</option>
<option value="IM">Isle of Man</option>
<option value="IL">Israel</option>
<option value="IT">Italy</option>
<option value="JM">Jamaica</option>
<option value="JP">Japan</option>
<option value="JE">Jersey</option>
<option value="JO">Jordan</option>
<option value="KZ">Kazakhstan</option>
<option value="KE">Kenya</option>
<option value="KI">Kiribati</option>
<option value="KP">Korea, Democratic People's Republic of</option>
<option value="KR">Korea, Republic of</option>
<option value="KW">Kuwait</option>
<option value="KG">Kyrgyzstan</option>
<option value="LA">Lao People's Democratic Republic</option>
<option value="LV">Latvia</option>
<option value="LB">Lebanon</option>
<option value="LS">Lesotho</option>
<option value="LR">Liberia</option>
<option value="LY">Libya</option>
<option value="LI">Liechtenstein</option>
<option value="LT">Lithuania</option>
<option value="LU">Luxembourg</option>
<option value="MO">Macao</option>
<option value="MK">Macedonia, the former Yugoslav Republic of</option>
<option value="MG">Madagascar</option>
<option value="MW">Malawi</option>
<option value="MY">Malaysia</option>
<option value="MV">Maldives</option>
<option value="ML">Mali</option>
<option value="MT">Malta</option>
<option value="MH">Marshall Islands</option>
<option value="MQ">Martinique</option>
<option value="MR">Mauritania</option>
<option value="MU">Mauritius</option>
<option value="YT">Mayotte</option>
<option value="MX">Mexico</option>
<option value="FM">Micronesia, Federated States of</option>
<option value="MD">Moldova, Republic of</option>
<option value="MC">Monaco</option>
<option value="MN">Mongolia</option>
<option value="ME">Montenegro</option>
<option value="MS">Montserrat</option>
<option value="MA">Morocco</option>
<option value="MZ">Mozambique</option>
<option value="MM">Myanmar</option>
<option value="NA">Namibia</option>
<option value="NR">Nauru</option>
<option value="NP">Nepal</option>
<option value="NL">Netherlands</option>
<option value="NC">New Caledonia</option>
<option value="NZ">New Zealand</option>
<option value="NI">Nicaragua</option>
<option value="NE">Niger</option>
<option value="NG">Nigeria</option>
<option value="NU">Niue</option>
<option value="NF">Norfolk Island</option>
<option value="MP">Northern Mariana Islands</option>
<option value="NO">Norway</option>
<option value="OM">Oman</option>
<option value="PK">Pakistan</option>
<option value="PW">Palau</option>
<option value="PS">Palestinian Territory, Occupied</option>
<option value="PA">Panama</option>
<option value="PG">Papua New Guinea</option>
<option value="PY">Paraguay</option>
<option value="PE">Peru</option>
<option value="PH">Philippines</option>
<option value="PN">Pitcairn</option>
<option value="PL">Poland</option>
<option value="PT">Portugal</option>
<option value="PR">Puerto Rico</option>
<option value="QA">Qatar</option>
<option value="RE">Réunion</option>
<option value="RO">Romania</option>
<option value="RU">Russian Federation</option>
<option value="RW">Rwanda</option>
<option value="BL">Saint Barthélemy</option>
<option value="SH">Saint Helena, Ascension and Tristan da Cunha</option>
<option value="KN">Saint Kitts and Nevis</option>
<option value="LC">Saint Lucia</option>
<option value="MF">Saint Martin (French part)</option>
<option value="PM">Saint Pierre and Miquelon</option>
<option value="VC">Saint Vincent and the Grenadines</option>
<option value="WS">Samoa</option>
<option value="SM">San Marino</option>
<option value="ST">Sao Tome and Principe</option>
<option value="SA">Saudi Arabia</option>
<option value="SN">Senegal</option>
<option value="RS">Serbia</option>
<option value="SC">Seychelles</option>
<option value="SL">Sierra Leone</option>
<option value="SG">Singapore</option>
<option value="SX">Sint Maarten (Dutch part)</option>
<option value="SK">Slovakia</option>
<option value="SI">Slovenia</option>
<option value="SB">Solomon Islands</option>
<option value="SO">Somalia</option>
<option value="ZA">South Africa</option>
<option value="GS">South Georgia and the South Sandwich Islands</option>
<option value="SS">South Sudan</option>
<option value="ES">Spain</option>
<option value="LK">Sri Lanka</option>
<option value="SD">Sudan</option>
<option value="SR">Suriname</option>
<option value="SJ">Svalbard and Jan Mayen</option>
<option value="SZ">Swaziland</option>
<option value="SE">Sweden</option>
<option value="CH">Switzerland</option>
<option value="SY">Syrian Arab Republic</option>
<option value="TW">Taiwan, Province of China</option>
<option value="TJ">Tajikistan</option>
<option value="TZ">Tanzania, United Republic of</option>
<option value="TH">Thailand</option>
<option value="TL">Timor-Leste</option>
<option value="TG">Togo</option>
<option value="TK">Tokelau</option>
<option value="TO">Tonga</option>
<option value="TT">Trinidad and Tobago</option>
<option value="TN">Tunisia</option>
<option value="TR">Turkey</option>
<option value="TM">Turkmenistan</option>
<option value="TC">Turks and Caicos Islands</option>
<option value="TV">Tuvalu</option>
<option value="UG">Uganda</option>
<option value="UA">Ukraine</option>
<option value="AE">United Arab Emirates</option>
<option value="UM">United States Minor Outlying Islands</option>
<option value="UY">Uruguay</option>
<option value="UZ">Uzbekistan</option>
<option value="VU">Vanuatu</option>
<option value="VE">Venezuela, Bolivarian Republic of</option>
<option value="VN">Viet Nam</option>
<option value="VG">Virgin Islands, British</option>
<option value="VI">Virgin Islands, U.S.</option>
<option value="WF">Wallis and Futuna</option>
<option value="EH">Western Sahara</option>
<option value="YE">Yemen</option>
<option value="ZM">Zambia</option>
<option value="ZW">Zimbabwe</option>
</select>
</div>
</div>
<div class="col-sm-6">
<div class="form-group" show-errors>
<label for="address_zip"
ng-bind="card.address_country === 'US' ? 'Zip Code' : 'Postal Code'"></label>
<input type="text" id="address_zip" ng-model="card.address_zip"
class="form-control" required name="address_zip" api-field />
</div>
</div>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Submit
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,13 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-file-text-o"></i> Change Plan</h4>
</div>
<form name="form" ng-submit="form.$valid && submit()" api-form="submitPromise">
<div class="modal-body">
Coming soon. In the meantime, please <a href="https://bitwarden.com/contact/" target="_blank">contact us</a>
if you would like to change your plan.
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,75 @@
<section class="content-header">
<h1>
Collections
<small>control what you share</small>
</h1>
</section>
<section class="content">
<div class="box">
<div class="box-header with-border">
&nbsp;
<div class="box-filters hidden-xs">
<div class="form-group form-group-sm has-feedback has-feedback-left">
<input type="text" id="search" class="form-control" placeholder="Search collections..."
style="width: 200px;" ng-model="filterSearch">
<span class="fa fa-search form-control-feedback text-muted" aria-hidden="true"></span>
</div>
</div>
<div class="box-tools">
<button type="button" class="btn btn-primary btn-sm btn-flat" ng-click="add()">
<i class="fa fa-fw fa-plus-circle"></i> New Collection
</button>
</div>
</div>
<div class="box-body" ng-class="{'no-padding': filteredCollections.length}">
<div ng-show="loading && !collections.length">
Loading...
</div>
<div ng-show="!filteredCollections.length && filterSearch">
No collections to list.
</div>
<div ng-show="!loading && !collections.length">
<p>There are no collections yet for your organization.</p>
<button type="button" ng-click="add()" class="btn btn-default btn-flat">Add a Collection</button>
</div>
<div class="table-responsive" ng-show="collections.length">
<table class="table table-striped table-hover table-vmiddle">
<tbody>
<tr ng-repeat="collection in filteredCollections = (collections | filter: (filterSearch || '') |
orderBy: ['name']) track by collection.id">
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="users(collection)">
<i class="fa fa-fw fa-users"></i> Users
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="groups(collection)">
<i class="fa fa-fw fa-sitemap"></i> Groups
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="delete(collection)" class="text-red">
<i class="fa fa-fw fa-trash"></i> Delete
</a>
</li>
</ul>
</div>
</td>
<td valign="middle">
<a href="javascript:void(0)" ng-click="edit(collection)">
{{collection.name}}
</a>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</section>

View File

@@ -0,0 +1,34 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-cubes"></i> Add New Collection</h4>
</div>
<form name="form" ng-submit="form.$valid && submit(model)" api-form="submitPromise">
<div class="modal-body">
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<div class="form-group" show-errors>
<label for="email">Name</label>
<input type="text" id="name" name="Name" ng-model="model.name" class="form-control" required api-field />
</div>
<div class="callout callout-default">
<h4><i class="fa fa-info-circle"></i> Note</h4>
<p>
After creating the collection, you can associate a user to it by selecting a specific user on the "People" page.
</p>
<p>
You can associate new logins to the collection from your organization's "Vault" or by sharing an existing
login from "My vault".
</p>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Submit
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,35 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-cubes"></i> Edit Collection</h4>
</div>
<form name="form" ng-submit="form.$valid && submit(collection)" api-form="submitPromise">
<div class="modal-body">
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<div class="form-group" show-errors>
<label for="email">Name</label>
<input type="text" id="name" name="Name" ng-model="collection.name" class="form-control" required api-field />
</div>
<div class="callout callout-default">
<h4><i class="fa fa-info-circle"></i> Note</h4>
<p>
Select "Users" from the listing options to manage existing users for this collection. Associate new users by
editing the user's access on the "People" page.
</p>
<p>
You can associate new logins to the collection from your organization's "Vault" or by sharing an existing
login from "My vault".
</p>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Submit
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -1,9 +1,9 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title" id="auditsModelLabel"><i class="fa fa-search"></i> Audits</h4>
<h4 class="modal-title"><i class="fa fa-sitemap"></i> Groups <small>{{collection.name}}</small></h4>
</div>
<div class="modal-body">
Coming soon...
Groups are coming soon to bitwarden Enterprise organizations.
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>

View File

@@ -0,0 +1,64 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-users"></i> User Access <small>{{collection.name}}</small></h4>
</div>
<div class="modal-body">
<div ng-show="loading && !users.length">
Loading...
</div>
<div ng-show="!loading && !users.length">
<p>
No users for this collection. You can associate a new user to this collection by
selecting a specific user on the "People" page.
</p>
</div>
<div class="table-responsive" ng-show="users.length" style="margin: 0;">
<table class="table table-striped table-hover table-vmiddle" style="margin: 0;">
<tbody>
<tr ng-repeat="user in users | orderBy: ['email']">
<td style="width: 70px;">
<div class="btn-group" data-append-to=".modal">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li ng-show="user.id">
<a href="javascript:void(0)" ng-click="remove(user)" class="text-red">
<i class="fa fa-fw fa-remove"></i> Remove
</a>
</li>
<li ng-show="!user.id">
<a href="javascript:void(0)">
No options...
</a>
</li>
</ul>
</div>
</td>
<td style="width: 45px;">
<letter-avatar data="{{user.name || user.email}}"></letter-avatar>
</td>
<td>
{{user.email}}
<div ng-if="user.name"><small class="text-muted">{{user.name}}</small></div>
</td>
<td style="width: 60px;" class="text-right">
<i class="fa fa-unlock" ng-show="user.accessAll" title="Can Access All Items"></i>
<i class="fa fa-pencil-square-o" ng-show="!user.readOnly" title="Can Edit"></i>
</td>
<td style="width: 100px;">
{{user.type | enumName: 'OrgUserType'}}
</td>
<td style="width: 120px;">
<span class="label {{user.status | enumLabelClass: 'OrgUserStatus'}}">
{{user.status | enumName: 'OrgUserStatus'}}
</span>
</td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>

View File

@@ -0,0 +1,32 @@
<section class="content-header">
<h1>
Dashboard
<small>{{orgProfile.name}}</small>
</h1>
</section>
<section class="content">
<div class="callout callout-warning" ng-if="!orgProfile.enabled">
<h4><i class="fa fa-warning"></i> Organization Disabled</h4>
<p>
This organization is currently disabled. Users will not see your shared logins or collections.
Contact us if you would like to reinstate this organization.
</p>
<a class="btn btn-default btn-flat" href="https://bitwarden.com/contact/" target="_blank">
Contact Us
</a>
</div>
<div class="box">
<div class="box-header with-border">
<h3 class="box-title">Let's Get Started!</h3>
</div>
<div class="box-body">
<p>Dashboard features are coming soon. Get started by inviting users and creating your collections.</p>
<a class="btn btn-default btn-flat" ui-sref="backend.org.people({orgId: orgProfile.id})">
Invite Users
</a>
<a class="btn btn-default btn-flat" ui-sref="backend.org.collections({orgId: orgProfile.id})">
Manage Collections
</a>
</div>
</div>
</section>

View File

@@ -0,0 +1,34 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-trash"></i> Delete Organization</h4>
</div>
<form name="form" ng-submit="form.$valid && submit()" api-form="submitPromise">
<div class="modal-body">
<p>
Continue below to delete this organization and all associated data. This data includes any collections and
their associated logins. Individual user accounts will remain, though they will not be associated to this
organization anymore.
</p>
<div class="callout callout-warning">
<h4><i class="fa fa-warning"></i> Warning</h4>
Deleting this organization is permanent. It cannot be undone.
</div>
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<div class="form-group" show-errors>
<label for="masterPassword">Master Password</label>
<input type="password" id="masterPassword" name="MasterPasswordHash" ng-model="masterPassword" class="form-control"
required api-field />
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Delete
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,16 @@
<section class="content-header">
<h1>
Groups
<small>organize your users</small>
</h1>
</section>
<section class="content">
<div class="box">
<div class="box-header with-border">
<h3 class="box-title">Coming soon...</h3>
</div>
<div class="box-body">
<p>Groups are coming soon to bitwarden Enterprise organizations.</p>
</div>
</div>
</section>

View File

@@ -0,0 +1,85 @@
<section class="content-header">
<h1>
People
<small>users for your organization</small>
</h1>
</section>
<section class="content">
<div class="box">
<div class="box-header with-border">
&nbsp;
<div class="box-filters hidden-xs">
<div class="form-group form-group-sm has-feedback has-feedback-left">
<input type="text" id="search" class="form-control" placeholder="Search people..."
style="width: 200px;" ng-model="filterSearch">
<span class="fa fa-search form-control-feedback text-muted" aria-hidden="true"></span>
</div>
</div>
<div class="box-tools">
<button type="button" class="btn btn-primary btn-sm btn-flat" ng-click="invite()">
<i class="fa fa-fw fa-plus-circle"></i> Invite User
</button>
</div>
</div>
<div class="box-body" ng-class="{'no-padding': filteredUsers.length}">
<div ng-show="!filteredUsers.length && !filterSearch">
Loading...
</div>
<div class="table-responsive" ng-show="filteredUsers.length">
<table class="table table-striped table-hover table-vmiddle">
<tbody>
<tr ng-repeat="user in filteredUsers = (users | filter: (filterSearch || '') |
orderBy: ['type', 'name', 'email']) track by user.id">
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="edit(user.id)">
<i class="fa fa-fw fa-pencil"></i> Edit
</a>
</li>
<li ng-show="user.status === 1">
<a href="javascript:void(0)" ng-click="confirm(user)">
<i class="fa fa-fw fa-check"></i> Confirm
</a>
</li>
<li ng-show="user.status === 0">
<a href="javascript:void(0)" ng-click="reinvite(user)">
<i class="fa fa-fw fa-envelope-o"></i> Re-send Invitation
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="delete(user)" class="text-red">
<i class="fa fa-fw fa-remove"></i> Remove
</a>
</li>
</ul>
</div>
</td>
<td style="width: 45px;">
<letter-avatar data="{{user.name || user.email}}"></letter-avatar>
</td>
<td>
<a href="javascript:void(0)" ng-click="edit(user.id)">{{user.email}}</a>
<i class="fa fa-unlock text-muted" ng-show="user.accessAll"
title="Can Access All Items"></i>
<div ng-if="user.name"><small class="text-muted">{{user.name}}</small></div>
</td>
<td style="width: 100px;">
{{user.type | enumName: 'OrgUserType'}}
</td>
<td style="width: 120px;">
<span class="label {{user.status | enumLabelClass: 'OrgUserStatus'}}">
{{user.status | enumName: 'OrgUserStatus'}}
</span>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</section>

View File

@@ -0,0 +1,101 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-user"></i> Edit User <small>{{email}}</small></h4>
</div>
<form name="form" ng-submit="form.$valid && submit()" api-form="submitPromise">
<div class="modal-body">
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<h4>User Type</h4>
<div class="form-group">
<div class="radio">
<label>
<input type="radio" id="user-type" ng-model="type" name="Type" value="2" ng-checked="type === 2">
<strong>User</strong> - A regular user with access to your organization's collections.
</label>
</div>
<div class="radio">
<label>
<input type="radio" ng-model="type" name="Type" value="1" ng-checked="type === 1">
<strong>Admin</strong> - Admins can manage collections and users for your organization.
</label>
</div>
<div class="radio">
<label>
<input type="radio" ng-model="type" name="Type" value="0" ng-checked="type === 0">
<strong>Owner</strong> - The highest access user that can manage all aspects of your organization.
</label>
</div>
</div>
<h4>Access</h4>
<div class="radio">
<label>
<input type="radio" ng-model="accessAll" name="AccessAll"
ng-value="true" ng-checked="accessAll">
This user can access and modify <u>all items</u>.
</label>
</div>
<div class="radio">
<label>
<input type="radio" ng-model="accessAll" name="AccessAll"
ng-value="false" ng-checked="!accessAll">
This user can access only the selected collections.
</label>
</div>
<div ng-show="!accessAll">
<div ng-show="loading && !collections.length">
Loading collections...
</div>
<div ng-show="!loading && !collections.length">
<p>No collections for your organization.</p>
</div>
<div class="table-responsive" ng-show="collections.length" style="margin: 0;">
<table class="table table-striped table-hover" style="margin: 0;">
<thead>
<tr>
<th style="width: 40px;">
<input type="checkbox"
ng-checked="allSelected()"
ng-click="toggleCollectionSelectionAll($event)">
</th>
<th>Name</th>
<th style="width: 100px; text-align: center;">Read Only</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="collection in collections | orderBy: ['name']">
<td valign="middle">
<input type="checkbox"
name="selectedCollections[]"
value="{{collection.id}}"
ng-checked="collectionSelected(collection)"
ng-click="toggleCollectionSelection(collection.id)">
</td>
<td valign="middle">
{{collection.name}}
</td>
<td style="text-align: center;" valign="middle">
<input type="checkbox"
name="selectedCollectionsReadonly[]"
value="{{collection.id}}"
ng-disabled="!collectionSelected(collection)"
ng-checked="collectionSelected(collection) && selectedCollections[collection.id].readOnly"
ng-click="toggleCollectionReadOnlySelection(collection.id)">
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Submit
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,109 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-user"></i> Invite User</h4>
</div>
<form name="inviteForm" ng-submit="inviteForm.$valid && submit(model)" api-form="submitPromise">
<div class="modal-body">
<p>
Invite a new user to your organization by entering their bitwarden account email address below. If they do not have
a bitwarden account already, they will be prompted to create a new account.
</p>
<div class="callout callout-danger validation-errors" ng-show="inviteForm.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in inviteForm.$errors">{{e}}</li>
</ul>
</div>
<div class="form-group" show-errors>
<label for="email">Email</label>
<input type="email" id="email" name="Email" ng-model="model.email" class="form-control" required api-field />
</div>
<h4>User Type</h4>
<div class="form-group">
<div class="radio">
<label>
<input type="radio" id="user-type" ng-model="model.type" name="Type" value="User">
<strong>User</strong> - A regular user with access to your organization's collections.
</label>
</div>
<div class="radio">
<label>
<input type="radio" ng-model="model.type" name="Type" value="Admin">
<strong>Admin</strong> - Admins can manage collections and users for your organization.
</label>
</div>
<div class="radio">
<label>
<input type="radio" ng-model="model.type" name="Type" value="Owner">
<strong>Owner</strong> - The highest access user that can manage all aspects of your organization.
</label>
</div>
</div>
<h4>Access</h4>
<div class="radio">
<label>
<input type="radio" ng-model="model.accessAll" name="AccessAll"
ng-value="true" ng-checked="model.accessAll">
This user can access and modify <u>all items</u>.
</label>
</div>
<div class="radio">
<label>
<input type="radio" ng-model="model.accessAll" name="AccessAll"
ng-value="false" ng-checked="!model.accessAll">
This user can access only the selected collections.
</label>
</div>
<div ng-show="!model.accessAll">
<div ng-show="loading && !collections.length">
Loading collections...
</div>
<div ng-show="!loading && !collections.length">
<p>No collections for your organization.</p>
</div>
<div class="table-responsive" ng-show="collections.length" style="margin: 0;">
<table class="table table-striped table-hover" style="margin: 0;">
<thead>
<tr>
<th style="width: 40px;">
<input type="checkbox"
ng-checked="allSelected()"
ng-click="toggleCollectionSelectionAll($event)">
</th>
<th>Name</th>
<th style="width: 100px; text-align: center;">Read Only</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="collection in collections | orderBy: ['name'] track by collection.id">
<td style="width: 40px;" valign="middle">
<input type="checkbox"
name="selectedCollections[]"
value="{{collection.id}}"
ng-checked="collectionSelected(collection)"
ng-click="toggleCollectionSelection(collection.id)">
</td>
<td valign="middle">
{{collection.name}}
</td>
<td style="width: 100px; text-align: center;" valign="middle">
<input type="checkbox"
name="selectedCollectionsReadonly[]"
value="{{collection.id}}"
ng-disabled="!collectionSelected(collection)"
ng-checked="collectionSelected(collection) && selectedCollections[collection.id].readOnly"
ng-click="toggleCollectionReadOnlySelection(collection.id)">
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="inviteForm.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="inviteForm.$loading"></i>Send Invite
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,65 @@
<section class="content-header">
<h1>
Settings
<small>manage your organization</small>
</h1>
</section>
<section class="content">
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">General</h3>
</div>
<form role="form" name="generalForm" ng-submit="generalForm.$valid && generalSave()" api-form="generalPromise">
<div class="box-body">
<div class="row">
<div class="col-sm-9">
<div class="callout callout-danger validation-errors" ng-show="generalForm.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in generalForm.$errors">{{e}}</li>
</ul>
</div>
<div class="form-group" show-errors>
<label for="name">Organization Name</label>
<input type="text" id="name" name="Name" ng-model="model.name" class="form-control"
required api-field />
</div>
<div class="form-group" show-errors>
<label for="name">Business Name</label>
<input type="text" id="businessName" name="BusinessName" ng-model="model.businessName"
class="form-control" api-field />
</div>
<div class="form-group" show-errors>
<label for="name">Billing Email</label>
<input type="email" id="billingEmail" name="BillingEmail" ng-model="model.billingEmail"
class="form-control" required api-field />
</div>
</div>
<div class="col-sm-3 settings-photo">
<letter-avatar data="{{model.name}}" round="false"
avclass="img-responsive img-rounded" avwidth="200" avheight="200"
fontsize="90"></letter-avatar>
</div>
</div>
</div>
<div class="box-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="generalForm.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="generalForm.$loading"></i>Save
</button>
</div>
</form>
</div>
<div class="box box-danger">
<div class="box-header with-border">
<h3 class="box-title">Danger Zone</h3>
</div>
<div class="box-body">
Careful, these actions are not reversible!
</div>
<div class="box-footer">
<button type="submit" class="btn btn-default btn-flat" ng-click="delete()">
Delete Organization
</button>
</div>
</div>
</section>

View File

@@ -0,0 +1,78 @@
<section class="content-header">
<h1>
Org<span class="hidden-xs">anization</span> Vault
<small>
<span ng-pluralize
count="collections.length > 0 ? collections.length - 1 : 0"
when="{'1': '{} collection', 'other': '{} collections'}"></span>,
<span ng-pluralize count="logins.length" when="{'1': '{} login', 'other': '{} logins'}"></span>
</small>
</h1>
</section>
<section class="content">
<p ng-show="loading && !collections.length">Loading...</p>
<div class="box" ng-class="{'collapsed-box': collection.collapsed}" ng-repeat="collection in collections |
orderBy: collectionSort track by collection.id"
ng-show="collections.length && (!main.searchVaultText || collectionLogins.length)">
<div class="box-header with-border">
<h3 class="box-title">
<i class="fa" ng-class="{'fa-cubes': collection.id, 'fa-sitemap': !collection.id}"></i>
{{collection.name}}
<small ng-pluralize count="collectionLogins.length" when="{'1': '{} login', 'other': '{} logins'}"></small>
</h3>
<div class="box-tools">
<button type="button" class="btn btn-box-tool" data-widget="collapse" title="Collapse/Expand"
ng-click="collapseExpand(collection)">
<i class="fa" ng-class="{'fa-minus': !collection.collapsed, 'fa-plus': collection.collapsed}"></i>
</button>
</div>
</div>
<div class="box-body" ng-class="{'no-padding': collectionLogins.length}">
<div ng-show="!collectionLogins.length && collection.id">No logins in this collection.</div>
<div ng-show="!collectionLogins.length && !collection.id">No unassigned logins.</div>
<div class="table-responsive" ng-show="collectionLogins.length">
<table class="table table-striped table-hover table-vmiddle">
<tbody>
<tr ng-repeat="login in collectionLogins = (logins | filter: filterByCollection(collection) |
filter: (main.searchVaultText || '') | orderBy: ['name', 'username']) track by login.id">
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="editLogin(login)">
<i class="fa fa-fw fa-pencil"></i> Edit
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="editCollections(login)">
<i class="fa fa-fw fa-cubes"></i> Collections
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="removeLogin(login, collection)" class="text-red"
ng-if="collection.id">
<i class="fa fa-fw fa-remove"></i> Remove
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="deleteLogin(login)" class="text-red">
<i class="fa fa-fw fa-trash"></i> Delete
</a>
</li>
</ul>
</div>
</td>
<td>
<a href="javascript:void(0)" ng-click="editLogin(login)">{{login.name}}</a>
<div class="text-sm text-muted">{{login.username}}</div>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</section>

View File

@@ -0,0 +1,52 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-cubes"></i> Collections <small>{{cipher.name}}</small></h4>
</div>
<form name="form" ng-submit="form.$valid && submit()" api-form="submitPromise">
<div class="modal-body">
<p>Edit the collections that this login is being shared with.</p>
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<div ng-show="!collections.length" class="callout callout-default">
<p>There are no collections yet for your organization.</p>
</div>
<div class="table-responsive" ng-show="collections.length" style="margin: 0;">
<table class="table table-striped table-hover" style="margin: 0;">
<thead>
<tr>
<th style="width: 40px;">
<input type="checkbox"
ng-checked="allSelected()"
ng-click="toggleCollectionSelectionAll($event)">
</th>
<th>Name</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="collection in collections | orderBy: ['name'] track by collection.id">
<td valign="middle">
<input type="checkbox"
name="selectedCollections[]"
value="{{collection.id}}"
ng-checked="collectionSelected(collection)"
ng-click="toggleCollectionSelection(collection.id)">
</td>
<td valign="middle" ng-click="toggleCollectionSelection(collection.id)">
{{collection.name}}
</td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading" ng-show="collections.length">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Save
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -36,12 +36,9 @@
</div>
</div>
<div class="col-sm-3 settings-photo">
<a href="http://www.gravatar.com/" target="_blank">
<img src="//www.gravatar.com/avatar/{{ main.userProfile.email | gravatar }}.jpg?s=150&d=mm"
class="img-rounded img-responsive" alt="User Image">
</a>
<a href="http://www.gravatar.com/" target="_blank" class="btn btn-link"
analytics-on="click" analytics-event="Clicked Update Photo">Update Photo</a>
<letter-avatar data="{{model.profile.name || model.email}}" round="false"
avclass="img-responsive img-rounded" avwidth="200" avheight="200"
fontsize="90"></letter-avatar>
</div>
</div>
</div>
@@ -109,6 +106,41 @@
</button>
</div>
</div>
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">Organizations</h3>
</div>
<div class="box-body" ng-if="!model.organizations || !model.organizations.length">
No organizations yet for your account.
</div>
<div class="list-group" ng-if="model.organizations && model.organizations.length">
<div class="list-group-item" ng-repeat="org in model.organizations | orderBy: ['name']">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="leaveOrganization(org)" class="text-red">
<i class="fa fa-fw fa-sign-out"></i> Leave
</a>
</li>
</ul>
</div>
<a href="javascript:void(0)" ng-click="viewOrganization(org)">
<letter-avatar data="{{org.name}}" round="false" avwidth="25" avheight="25"
avclass="img-rounded" fontsize="10"></letter-avatar>
{{org.name}}
<span class="label bg-gray" ng-if="!org.enabled">DISABLED</span>
</a>
</div>
</div>
<div class="box-footer">
<a ui-sref="backend.user.settingsCreateOrg" class="btn btn-default btn-flat">
Create an Organization
</a>
</div>
</div>
<div class="box box-danger">
<div class="box-header with-border">
<h3 class="box-title">Danger Zone</h3>

View File

@@ -0,0 +1,535 @@
<section class="content-header">
<h1>Create Organization</h1>
</section>
<section class="content">
<p>
Organizations allow you to share parts of your vault with others as well as manage related users
for a specific entity (such as a family, small team, or large company).
</p>
<form name="createOrgForm" ng-submit="createOrgForm.$valid && submit(model)" api-form="submitPromise">
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">General Information</h3>
</div>
<div class="box-body">
<div class="callout callout-danger validation-errors" ng-show="createOrgForm.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in createOrgForm.$errors">{{e}}</li>
</ul>
</div>
<div class="row">
<div class="col-md-6">
<div class="form-group" show-errors>
<label for="name">Organization Name</label>
<input type="text" id="name" name="Name" ng-model="model.name" class="form-control"
required api-field />
</div>
</div>
<div class="col-md-6">
<div class="form-group" show-errors>
<label for="billingEmail">Billing Email</label>
<input type="email" id="billingEmail" name="BillingEmail" ng-model="model.billingEmail"
class="form-control" required api-field />
</div>
</div>
</div>
<div class="checkbox">
<label>
<input type="checkbox" ng-model="model.ownedBusiness" ng-click="changedBusiness()">
This account is owned by a business.
</label>
</div>
<div class="row" ng-show="model.ownedBusiness">
<div class="col-md-6">
<div class="form-group" show-errors>
<label for="businessName">Business Name</label>
<input type="text" id="businessName" name="BusinessName" ng-model="model.businessName"
class="form-control" api-field />
</div>
</div>
</div>
</div>
</div>
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">Choose Your Plan</h3>
</div>
<div class="box-body">
<div class="radio radio-block" ng-if="!model.ownedBusiness" ng-click="changedPlan()">
<label>
<input type="radio" ng-model="model.plan" name="PlanType" value="free">
Free
<span>For personal users to share with 1 other user.</span>
<span>- Limit 2 users (including you)</span>
<span>- Limit 2 collections</span>
<span class="bottom-line">
Free forever
</span>
</label>
</div>
<div class="radio radio-block" ng-if="!model.ownedBusiness" ng-click="changedPlan()">
<label>
<input type="radio" ng-model="model.plan" name="PlanType" value="personal">
Personal
<span>For personal users such as families &amp; friends.</span>
<span>- Add and share with up to 10 users (5 included with base price)</span>
<span>- Create unlimited collections</span>
<span>- Priority customer support</span>
<span>- 7 day free trial, cancel anytime</span>
<span class="bottom-line">
{{plans.personal.basePrice | currency:'$'}} /month for {{plans.personal.baseSeats}} users,
additional users {{plans.personal.seatPrice | currency:'$'}} /month
</span>
</label>
</div>
<div class="radio radio-block" ng-click="changedPlan()">
<label>
<input type="radio" ng-model="model.plan" name="PlanType" value="teams">
Teams
<span>For businesses and other team organizations.</span>
<span>- Add and share with unlimited users</span>
<span>- Create unlimited collections</span>
<span>- Priority customer support</span>
<span>- 7 day free trial, cancel anytime</span>
<span class="bottom-line">
{{plans.teams.basePrice | currency:'$'}} /month for {{plans.teams.baseSeats}} users,
additional users {{plans.teams.seatPrice | currency:'$'}} /month
</span>
</label>
</div>
</div>
<div class="box-footer" ng-show="plans[model.plan].noPayment">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="createOrgForm.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="createOrgForm.$loading"></i>Submit
</button>
</div>
</div>
<div class="box box-default" ng-if="!plans[model.plan].noAdditionalSeats">
<div class="box-header with-border">
<h3 class="box-title">Additional Users (Seats)</h3>
</div>
<div class="box-body">
<p>
Your plan comes with <b>{{plans[model.plan].baseSeats}}</b> users (seats). You can add additional users
<span ng-if="plans[model.plan].maxAdditionalSeats">
(up to {{plans[model.plan].maxAdditionalSeats}} more)
</span>
for {{plans[model.plan].seatPrice | currency:'$'}} per user /month.
</p>
<div class="row">
<div class="col-md-4">
<div class="form-group" show-errors style="margin: 0;">
<label for="additionalSeats" class="sr-only">Additional Users</label>
<input type="number" id="additionalSeats" name="AdditionalSeats" ng-model="model.additionalSeats"
min="0" class="form-control" placeholder="# of users" api-field
ng-attr-max="{{plans[model.plan].maxAdditionalSeats || 1000000}}" />
</div>
</div>
</div>
</div>
</div>
<div class="box box-default" ng-if="!plans[model.plan].noPayment">
<div class="box-header with-border">
<h3 class="box-title">Billing Summary</h3>
</div>
<div class="box-body">
<div class="radio radio-block">
<label>
<input type="radio" ng-model="model.interval" name="BillingInterval" value="year">
Annually
<span>
Base price:
{{plans[model.plan].basePrice | currency:"$":2}} &times;12 mo. =
{{plans[model.plan].annualBasePrice | currency:"$":2}} /year
</span>
<span>
Additional users:
{{model.additionalSeats || 0}} &times;{{plans[model.plan].seatPrice | currency:"$":2}}
&times;12 mo. = {{(model.additionalSeats * plans[model.plan].annualSeatPrice) | currency:"$":2}} /year
</span>
</label>
</div>
<div class="radio radio-block" ng-if="model.plan !== 'personal'">
<label>
<input type="radio" ng-model="model.interval" name="BillingInterval" value="month">
Monthly
<span>
Base price:
{{plans[model.plan].monthlyBasePrice | currency:"$":2}} /month
</span>
<span>
Additional users:
{{model.additionalSeats || 0}} &times;{{plans[model.plan].monthlySeatPrice | currency:"$":2}} =
{{(model.additionalSeats * plans[model.plan].monthlySeatPrice) | currency:"$":2}} /month
</span>
</label>
</div>
</div>
<div class="box-footer">
<h4>
<b>Total:</b>
{{totalPrice() | currency:"USD $":2}} /{{model.interval}}
</h4>
Your plan comes with a free 7 day trial. Your card will not be charged until the trial has ended.
You may cancel at any time.
</div>
</div>
<div class="box box-default" ng-if="!plans[model.plan].noPayment">
<div class="box-header with-border">
<h3 class="box-title">Payment Information</h3>
</div>
<div class="box-body">
<div class="row">
<div class="col-md-5">
<div class="form-group" show-errors>
<label for="card_number">Card Number</label>
<input type="text" id="card_number" name="card_number" ng-model="model.card.number"
class="form-control" cc-number required api-field />
</div>
</div>
<div class="col-md-7">
<br class="hidden-sm hidden-xs" />
<ul class="list-inline" style="margin: 0;">
<li><div class="cc visa"></div></li>
<li><div class="cc mastercard"></div></li>
<li><div class="cc amex"></div></li>
<li><div class="cc discover"></div></li>
<li><div class="cc diners"></div></li>
<li><div class="cc jcb"></div></li>
</ul>
</div>
</div>
<div class="row">
<div class="col-sm-4">
<div class="form-group" show-errors>
<label for="exp_month">Expiration Month</label>
<select id="exp_month" class="form-control" ng-model="model.card.exp_month" required cc-exp-month
name="exp_month" api-field>
<option value="">-- Select --</option>
<option value="01">01 - January</option>
<option value="02">02 - February</option>
<option value="03">03 - March</option>
<option value="04">04 - April</option>
<option value="05">05 - May</option>
<option value="06">06 - June</option>
<option value="07">07 - July</option>
<option value="08">08 - August</option>
<option value="09">09 - September</option>
<option value="10">10 - October</option>
<option value="11">11 - November</option>
<option value="12">12 - December</option>
</select>
</div>
</div>
<div class="col-sm-4">
<div class="form-group" show-errors>
<label for="exp_year">Expiration Year</label>
<select id="exp_year" class="form-control" ng-model="model.card.exp_year" required cc-exp-year
name="exp_year" api-field>
<option value="">-- Select --</option>
<option value="17">2017</option>
<option value="18">2018</option>
<option value="19">2019</option>
<option value="20">2020</option>
<option value="21">2021</option>
<option value="22">2022</option>
<option value="23">2023</option>
<option value="24">2024</option>
<option value="25">2025</option>
<option value="26">2026</option>
</select>
</div>
</div>
<div class="col-sm-4">
<div class="form-group" show-errors>
<label for="cvc">
CVC
<a href="https://www.cvvnumber.com/cvv.html" target="_blank" title="What is this?"
rel="noopener noreferrer">
<i class="fa fa-question-circle"></i>
</a>
</label>
<input type="text" id="cvc" ng-model="model.card.cvc" class="form-control" name="cvc"
cc-type="number.$ccType" cc-cvc required api-field />
</div>
</div>
</div>
<div class="row">
<div class="col-sm-6">
<div class="form-group" show-errors>
<label for="address_country">Country</label>
<select id="address_country" class="form-control" ng-model="model.card.address_country"
required name="address_country" api-field>
<option value="">-- Select --</option>
<option value="US">United States</option>
<option value="CN">China</option>
<option value="FR">France</option>
<option value="DE">Germany</option>
<option value="CA">Canada</option>
<option value="GB">United Kingdom</option>
<option value="AU">Australia</option>
<option value="IN">India</option>
<option value="-" disabled></option>
<option value="AF">Afghanistan</option>
<option value="AX">Åland Islands</option>
<option value="AL">Albania</option>
<option value="DZ">Algeria</option>
<option value="AS">American Samoa</option>
<option value="AD">Andorra</option>
<option value="AO">Angola</option>
<option value="AI">Anguilla</option>
<option value="AQ">Antarctica</option>
<option value="AG">Antigua and Barbuda</option>
<option value="AR">Argentina</option>
<option value="AM">Armenia</option>
<option value="AW">Aruba</option>
<option value="AT">Austria</option>
<option value="AZ">Azerbaijan</option>
<option value="BS">Bahamas</option>
<option value="BH">Bahrain</option>
<option value="BD">Bangladesh</option>
<option value="BB">Barbados</option>
<option value="BY">Belarus</option>
<option value="BE">Belgium</option>
<option value="BZ">Belize</option>
<option value="BJ">Benin</option>
<option value="BM">Bermuda</option>
<option value="BT">Bhutan</option>
<option value="BO">Bolivia, Plurinational State of</option>
<option value="BQ">Bonaire, Sint Eustatius and Saba</option>
<option value="BA">Bosnia and Herzegovina</option>
<option value="BW">Botswana</option>
<option value="BV">Bouvet Island</option>
<option value="BR">Brazil</option>
<option value="IO">British Indian Ocean Territory</option>
<option value="BN">Brunei Darussalam</option>
<option value="BG">Bulgaria</option>
<option value="BF">Burkina Faso</option>
<option value="BI">Burundi</option>
<option value="KH">Cambodia</option>
<option value="CM">Cameroon</option>
<option value="CV">Cape Verde</option>
<option value="KY">Cayman Islands</option>
<option value="CF">Central African Republic</option>
<option value="TD">Chad</option>
<option value="CL">Chile</option>
<option value="CX">Christmas Island</option>
<option value="CC">Cocos (Keeling) Islands</option>
<option value="CO">Colombia</option>
<option value="KM">Comoros</option>
<option value="CG">Congo</option>
<option value="CD">Congo, the Democratic Republic of the</option>
<option value="CK">Cook Islands</option>
<option value="CR">Costa Rica</option>
<option value="CI">Côte d'Ivoire</option>
<option value="HR">Croatia</option>
<option value="CU">Cuba</option>
<option value="CW">Curaçao</option>
<option value="CY">Cyprus</option>
<option value="CZ">Czech Republic</option>
<option value="DK">Denmark</option>
<option value="DJ">Djibouti</option>
<option value="DM">Dominica</option>
<option value="DO">Dominican Republic</option>
<option value="EC">Ecuador</option>
<option value="EG">Egypt</option>
<option value="SV">El Salvador</option>
<option value="GQ">Equatorial Guinea</option>
<option value="ER">Eritrea</option>
<option value="EE">Estonia</option>
<option value="ET">Ethiopia</option>
<option value="FK">Falkland Islands (Malvinas)</option>
<option value="FO">Faroe Islands</option>
<option value="FJ">Fiji</option>
<option value="FI">Finland</option>
<option value="GF">French Guiana</option>
<option value="PF">French Polynesia</option>
<option value="TF">French Southern Territories</option>
<option value="GA">Gabon</option>
<option value="GM">Gambia</option>
<option value="GE">Georgia</option>
<option value="GH">Ghana</option>
<option value="GI">Gibraltar</option>
<option value="GR">Greece</option>
<option value="GL">Greenland</option>
<option value="GD">Grenada</option>
<option value="GP">Guadeloupe</option>
<option value="GU">Guam</option>
<option value="GT">Guatemala</option>
<option value="GG">Guernsey</option>
<option value="GN">Guinea</option>
<option value="GW">Guinea-Bissau</option>
<option value="GY">Guyana</option>
<option value="HT">Haiti</option>
<option value="HM">Heard Island and McDonald Islands</option>
<option value="VA">Holy See (Vatican City State)</option>
<option value="HN">Honduras</option>
<option value="HK">Hong Kong</option>
<option value="HU">Hungary</option>
<option value="IS">Iceland</option>
<option value="ID">Indonesia</option>
<option value="IR">Iran, Islamic Republic of</option>
<option value="IQ">Iraq</option>
<option value="IE">Ireland</option>
<option value="IM">Isle of Man</option>
<option value="IL">Israel</option>
<option value="IT">Italy</option>
<option value="JM">Jamaica</option>
<option value="JP">Japan</option>
<option value="JE">Jersey</option>
<option value="JO">Jordan</option>
<option value="KZ">Kazakhstan</option>
<option value="KE">Kenya</option>
<option value="KI">Kiribati</option>
<option value="KP">Korea, Democratic People's Republic of</option>
<option value="KR">Korea, Republic of</option>
<option value="KW">Kuwait</option>
<option value="KG">Kyrgyzstan</option>
<option value="LA">Lao People's Democratic Republic</option>
<option value="LV">Latvia</option>
<option value="LB">Lebanon</option>
<option value="LS">Lesotho</option>
<option value="LR">Liberia</option>
<option value="LY">Libya</option>
<option value="LI">Liechtenstein</option>
<option value="LT">Lithuania</option>
<option value="LU">Luxembourg</option>
<option value="MO">Macao</option>
<option value="MK">Macedonia, the former Yugoslav Republic of</option>
<option value="MG">Madagascar</option>
<option value="MW">Malawi</option>
<option value="MY">Malaysia</option>
<option value="MV">Maldives</option>
<option value="ML">Mali</option>
<option value="MT">Malta</option>
<option value="MH">Marshall Islands</option>
<option value="MQ">Martinique</option>
<option value="MR">Mauritania</option>
<option value="MU">Mauritius</option>
<option value="YT">Mayotte</option>
<option value="MX">Mexico</option>
<option value="FM">Micronesia, Federated States of</option>
<option value="MD">Moldova, Republic of</option>
<option value="MC">Monaco</option>
<option value="MN">Mongolia</option>
<option value="ME">Montenegro</option>
<option value="MS">Montserrat</option>
<option value="MA">Morocco</option>
<option value="MZ">Mozambique</option>
<option value="MM">Myanmar</option>
<option value="NA">Namibia</option>
<option value="NR">Nauru</option>
<option value="NP">Nepal</option>
<option value="NL">Netherlands</option>
<option value="NC">New Caledonia</option>
<option value="NZ">New Zealand</option>
<option value="NI">Nicaragua</option>
<option value="NE">Niger</option>
<option value="NG">Nigeria</option>
<option value="NU">Niue</option>
<option value="NF">Norfolk Island</option>
<option value="MP">Northern Mariana Islands</option>
<option value="NO">Norway</option>
<option value="OM">Oman</option>
<option value="PK">Pakistan</option>
<option value="PW">Palau</option>
<option value="PS">Palestinian Territory, Occupied</option>
<option value="PA">Panama</option>
<option value="PG">Papua New Guinea</option>
<option value="PY">Paraguay</option>
<option value="PE">Peru</option>
<option value="PH">Philippines</option>
<option value="PN">Pitcairn</option>
<option value="PL">Poland</option>
<option value="PT">Portugal</option>
<option value="PR">Puerto Rico</option>
<option value="QA">Qatar</option>
<option value="RE">Réunion</option>
<option value="RO">Romania</option>
<option value="RU">Russian Federation</option>
<option value="RW">Rwanda</option>
<option value="BL">Saint Barthélemy</option>
<option value="SH">Saint Helena, Ascension and Tristan da Cunha</option>
<option value="KN">Saint Kitts and Nevis</option>
<option value="LC">Saint Lucia</option>
<option value="MF">Saint Martin (French part)</option>
<option value="PM">Saint Pierre and Miquelon</option>
<option value="VC">Saint Vincent and the Grenadines</option>
<option value="WS">Samoa</option>
<option value="SM">San Marino</option>
<option value="ST">Sao Tome and Principe</option>
<option value="SA">Saudi Arabia</option>
<option value="SN">Senegal</option>
<option value="RS">Serbia</option>
<option value="SC">Seychelles</option>
<option value="SL">Sierra Leone</option>
<option value="SG">Singapore</option>
<option value="SX">Sint Maarten (Dutch part)</option>
<option value="SK">Slovakia</option>
<option value="SI">Slovenia</option>
<option value="SB">Solomon Islands</option>
<option value="SO">Somalia</option>
<option value="ZA">South Africa</option>
<option value="GS">South Georgia and the South Sandwich Islands</option>
<option value="SS">South Sudan</option>
<option value="ES">Spain</option>
<option value="LK">Sri Lanka</option>
<option value="SD">Sudan</option>
<option value="SR">Suriname</option>
<option value="SJ">Svalbard and Jan Mayen</option>
<option value="SZ">Swaziland</option>
<option value="SE">Sweden</option>
<option value="CH">Switzerland</option>
<option value="SY">Syrian Arab Republic</option>
<option value="TW">Taiwan, Province of China</option>
<option value="TJ">Tajikistan</option>
<option value="TZ">Tanzania, United Republic of</option>
<option value="TH">Thailand</option>
<option value="TL">Timor-Leste</option>
<option value="TG">Togo</option>
<option value="TK">Tokelau</option>
<option value="TO">Tonga</option>
<option value="TT">Trinidad and Tobago</option>
<option value="TN">Tunisia</option>
<option value="TR">Turkey</option>
<option value="TM">Turkmenistan</option>
<option value="TC">Turks and Caicos Islands</option>
<option value="TV">Tuvalu</option>
<option value="UG">Uganda</option>
<option value="UA">Ukraine</option>
<option value="AE">United Arab Emirates</option>
<option value="UM">United States Minor Outlying Islands</option>
<option value="UY">Uruguay</option>
<option value="UZ">Uzbekistan</option>
<option value="VU">Vanuatu</option>
<option value="VE">Venezuela, Bolivarian Republic of</option>
<option value="VN">Viet Nam</option>
<option value="VG">Virgin Islands, British</option>
<option value="VI">Virgin Islands, U.S.</option>
<option value="WF">Wallis and Futuna</option>
<option value="EH">Western Sahara</option>
<option value="YE">Yemen</option>
<option value="ZM">Zambia</option>
<option value="ZW">Zimbabwe</option>
</select>
</div>
</div>
<div class="col-sm-4">
<div class="form-group" show-errors>
<label for="address_zip"
ng-bind="model.card.address_country === 'US' ? 'Zip Code' : 'Postal Code'"></label>
<input type="text" id="address_zip" ng-model="model.card.address_zip"
class="form-control" required name="address_zip" api-field />
</div>
</div>
</div>
</div>
<div class="box-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="createOrgForm.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="createOrgForm.$loading"></i>Submit
</button>
</div>
</div>
</form>
</section>

View File

@@ -9,25 +9,36 @@
<form name="customForm" ng-submit="customForm.$valid && saveCustom()" api-form="customPromise">
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">Custom Equivalent Domains</h3>
<div class="box-tools pull-right">
<button type="button" class="btn btn-box-tool" ng-click="addEdit(null)">
<i class="fa fa-plus"></i> Add New
<h3 class="box-title">Custom <span class="hidden-xs">Equivalent Domains</span></h3>
<div class="box-tools">
<button type="button" class="btn btn-primary btn-sm btn-flat" ng-click="addEdit(null)">
<i class="fa fa-fw fa-plus-circle"></i> New Domain
</button>
</div>
</div>
<div class="box-body no-padding">
<div class="table-responsive">
<table class="table table-striped table-hover">
<table class="table table-striped table-hover table-vmiddle">
<tbody ng-if="equivalentDomains.length">
<tr ng-repeat="customDomain in equivalentDomains track by $index">
<td style="width: 80px; min-width: 80px;">
<button type="button" class="btn btn-link btn-table" uib-tooltip="Edit" ng-click="addEdit($index)">
<i class="fa fa-lg fa-pencil"></i>
</button>
<button type="button" class="btn btn-link btn-table" uib-tooltip="Delete" ng-click="delete($index)">
<i class="fa fa-lg fa-trash"></i>
</button>
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="addEdit($index)">
<i class="fa fa-fw fa-pencil"></i> Edit
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="delete($index)" class="text-red">
<i class="fa fa-fw fa-trash"></i> Delete
</a>
</li>
</ul>
</div>
</td>
<td>{{customDomain}}</td>
</tr>
@@ -51,28 +62,40 @@
<form name="globalForm" ng-submit="globalForm.$valid && saveGlobal()" api-form="globalPromise">
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">Global Equivalent Domains</h3>
<h3 class="box-title">Global <span class="hidden-xs">Equivalent Domains</span></h3>
</div>
<div class="box-body no-padding">
<div class="table-responsive">
<table class="table table-striped table-hover">
<table class="table table-striped table-hover table-vmiddle">
<tbody ng-if="globalEquivalentDomains.length">
<tr ng-repeat="globalDomain in globalEquivalentDomains">
<td style="width: 80px; min-width: 80px;">
<button type="button" class="btn btn-link btn-table" uib-tooltip="Exclude"
ng-if="!globalDomain.excluded" ng-click="toggleExclude(globalDomain)">
<i class="fa fa-lg fa-ban"></i>
</button>
<button type="button" class="btn btn-link btn-table" uib-tooltip="Include"
ng-if="globalDomain.excluded" ng-click="toggleExclude(globalDomain)">
<i class="fa fa-lg fa-plus"></i>
</button>
<button type="button" class="btn btn-link btn-table" uib-tooltip="Customize"
ng-click="customize(globalDomain)">
<i class="fa fa-lg fa-cut"></i>
</button>
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-if="!globalDomain.excluded"
ng-click="toggleExclude(globalDomain)">
<i class="fa fa-fw fa-remove"></i> Exclude
</a>
</li>
<li>
<a href="javascript:void(0)" ng-if="globalDomain.excluded"
ng-click="toggleExclude(globalDomain)">
<i class="fa fa-fw fa-plus"></i> Include
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="customize(globalDomain)">
<i class="fa fa-fw fa-cut"></i> Customize
</a>
</li>
</ul>
</div>
</td>
<td ng-class="{strike: globalDomain.excluded}">{{globalDomain.domains}}</td>
<td ng-class="{strike: globalDomain.excluded}">{{::globalDomain.domains}}</td>
</tr>
</tbody>
<tbody ng-if="!globalEquivalentDomains.length">

View File

@@ -2,9 +2,13 @@
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title" id="twoFactorModelLabel"><i class="fa fa-key"></i> Two-step Log In</h4>
</div>
<form name="authTwoStepForm" ng-submit="authTwoStepForm.$valid && auth(authModel)" api-form="authPromise" ng-if="!twoFactorModel">
<form name="authTwoStepForm" ng-submit="authTwoStepForm.$valid && auth(authModel)" api-form="authPromise"
ng-if="!twoFactorModel">
<div class="modal-body">
<p ng-show="enabled()">Two-step log in is already enabled on your account. To access your two-step settings enter your master password below.</p>
<p ng-show="enabled()">
Two-step log in is already enabled on your account. To access your two-step
settings enter your master password below.
</p>
<p ng-show="!enabled()">To get started with two-step log in enter your master password below.</p>
<div class="callout callout-danger validation-errors" ng-show="authTwoStepForm.$errors">
<h4>Errors have occured</h4>
@@ -14,7 +18,8 @@
</div>
<div class="form-group" show-errors>
<label for="masterPassword">Master Password</label>
<input type="password" id="masterPassword" name="MasterPasswordHash" ng-model="authModel.masterPassword" class="form-control" required api-field />
<input type="password" id="masterPassword" name="MasterPasswordHash" ng-model="authModel.masterPassword"
class="form-control" required api-field />
</div>
</div>
<div class="modal-footer">
@@ -24,10 +29,17 @@
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>
<form name="updateTwoStepForm" ng-submit="updateTwoStepForm.$valid && update(updateModel)" api-form="updatePromise" ng-if="twoFactorModel">
<form name="updateTwoStepForm" ng-submit="updateTwoStepForm.$valid && update(updateModel)" api-form="updatePromise"
ng-if="twoFactorModel">
<div class="modal-body">
<div ng-show="enabled()">
<p>Two-step log in is <strong class="text-green">enabled</strong> on your account. Below is the code required by your verification app.</p>
<div class="callout callout-success">
<h4><i class="fa fa-check-circle"></i> Enabled</h4>
<p>
Two-step log in is enabled on your account. Incase you need to add it to another device, below is the QR
code (or key) required by your verification app.
</p>
</div>
<p>Need a two-step verification app? Download one of the following:</p>
</div>
<div ng-show="!enabled()">
@@ -35,10 +47,29 @@
<h4>1. Download a two-step verification app</h4>
</div>
<ul class="fa-ul">
<li><i class="fa-li fa fa-apple"></i> iOS devices: <a href="https://itunes.apple.com/us/app/authy/id494168017?mt=8" target="_blank">Authy for iOS</a></li>
<li><i class="fa-li fa fa-android"></i> Android devices: <a href="https://play.google.com/store/apps/details?id=com.authy.authy" target="_blank">Authy for Android</a></li>
<li><i class="fa-li fa fa-windows"></i> Windows devices: <a href="https://www.microsoft.com/en-us/store/apps/authenticator/9wzdncrfj3rj" target="_blank">Microsoft Authenticator </a></li>
<li>
<i class="fa-li fa fa-apple fa-lg"></i>
iOS devices:
<a href="https://itunes.apple.com/us/app/authy/id494168017?mt=8" target="_blank">
Authy for iOS
</a>
</li>
<li>
<i class="fa-li fa fa-android fa-lg"></i>
Android devices:
<a href="https://play.google.com/store/apps/details?id=com.authy.authy" target="_blank">
Authy for Android
</a>
</li>
<li>
<i class="fa-li fa fa-windows fa-lg"></i>
Windows devices:
<a href="https://www.microsoft.com/en-us/store/apps/authenticator/9wzdncrfj3rj" target="_blank">
Microsoft Authenticator
</a>
</li>
</ul>
<p>These apps are recommended, however, other authenticator apps will also work.</p>
<hr ng-show="enabled()" />
<h4 ng-show="!enabled()" style="margin-top: 30px;">2. Scan this QR code with your verification app</h4>
<div class="row">
@@ -46,7 +77,10 @@
<p><img ng-src="{{twoFactorModel.qr}}" alt="QR" class="img-thumbnail" /></p>
</div>
<div class="col-md-8">
<p><strong>Can't scan the code?</strong> You can add the code to your application manually using the following details:</p>
<p>
<strong>Can't scan the code?</strong> You can add the code to your application manually using the
following details:
</p>
<ul class="list-unstyled">
<li><strong>Key:</strong> <code>{{twoFactorModel.key}}</code></li>
<li><strong>Account:</strong> {{account}}</li>
@@ -56,12 +90,12 @@
</div>
<div ng-show="enabled()">
<hr />
<div class="callout callout-danger">
<div class="callout callout-warning">
<h4><i class="fa fa-warning"></i> Recovery Code <i class="fa fa-warning"></i></h4>
<p>
The recovery code allows you to access your account in the event that you lose your authenticator app.
bitwarden support won't be able to assist you if you lose access to your account. We recommend you write down or
print the recovery code below and keep it in a safe place.
bitwarden support won't be able to assist you if you lose access to your account. We recommend
you write down or print the recovery code below and keep it in a safe place.
</p>
<p><strong>Recovery Code:</strong> <code>{{twoFactorModel.recovery}}</code></p>
<button type="button" class="btn btn-default" ng-click="print(twoFactorModel.recovery)">
@@ -69,19 +103,26 @@
</button>
</div>
</div>
<hr ng-show="enabled()" />
<div class="callout callout-danger validation-errors" ng-show="updateTwoStepForm.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in updateTwoStepForm.$errors">{{e}}</li>
</ul>
</div>
<hr ng-show="enabled()" />
<h4 style="margin-top: 30px;"><span ng-show="enabled()">Want to disable? </span><span ng-show="!enabled()">3. </span>Enter the resulting verification code from the app</h4>
<h4 style="margin-top: 30px;">
<span ng-show="enabled()">Want to disable? </span><span ng-show="!enabled()">3. </span>
Enter the resulting verification code from the app
</h4>
<div class="form-group" show-errors>
<label for="token" class="sr-only">Verification Code</label>
<input type="text" id="token" name="Token" placeholder="Verification Code" ng-model="updateModel.token" class="form-control" required api-field />
<input type="text" id="token" name="Token" placeholder="Verification Code" ng-model="updateModel.token"
class="form-control" required api-field />
</div>
<p ng-show="!enabled()">NOTE: After enabling two-step log in, you will be required to enter the current code generated by your verification app each time you log in.</p>
<p ng-show="!enabled()">
NOTE: After enabling two-step log in, you will be required to enter the current code
generated by your verification app each time you log in.
</p>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="updateTwoStepForm.$loading">

View File

@@ -7,24 +7,17 @@
<section class="content">
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">Import</h3>
<h3 class="box-title">Import/Export</h3>
</div>
<div class="box-body">
Quickly import your logins and other data from a previous bitwarden export or from another
password manager application.
<p>
Quickly import your logins and other data from a previous export or from another
password management application.
</p>
<p>You can also export all of your vault data in <code>.csv</code> format.</p>
</div>
<div class="box-footer">
<button class="btn btn-default btn-flat" type="button" ng-click="import()">Import Data</button>
</div>
</div>
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">Export</h3>
</div>
<div class="box-body">
Export all of your vault data in <code>.csv</code> format.
</div>
<div class="box-footer">
<button class="btn btn-default btn-flat" type="button" ng-click="export()">Export Data</button>
</div>
</div>
@@ -36,12 +29,4 @@
Password generator is currently available in all other client applications. Coming soon to the web vault!
</div>
</div>
<div class="box box-default">
<div class="box-header with-border">
<h3 class="box-title">Audits</h3>
</div>
<div class="box-body">
Coming soon!
</div>
</div>
</section>

View File

@@ -2,21 +2,33 @@
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title" id="importModelLabel"><i class="fa fa-cloud-upload"></i> Import</h4>
</div>
<form name="importForm" ng-submit="importForm.$valid && import(model)" ng-show="!processing">
<form name="importForm" ng-submit="importForm.$valid && import(model, importForm)" ng-show="!processing">
<div class="modal-body">
<div class="callout callout-danger validation-errors" ng-show="importForm.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in importForm.$errors">{{e}}</li>
</ul>
</div>
<div class="form-group">
<label for="source">1. Select the source of this import file</label>
<select id="source" name="source" class="form-control" ng-model="model.source" ng-change="setSource()">
<label for="source">1. Select the format of the import file</label>
<select id="source" name="source" class="form-control" ng-model="model.source" ng-change="setSource()" required>
<option value="">-- Select --</option>
<option ng-repeat="option in options" value="{{option.id}}">{{option.name}}</option>
</select>
</div>
<div class="callout callout-default">
<div class="callout callout-default" ng-show="model.source">
<h4><i class="fa fa-info-circle"></i> {{source.name}} Instructions</h4>
<div ng-bind-html="source.instructions"></div>
</div>
<div class="form-group">
<label for="file">2. Select the import file</label>
<input type="file" id="file" name="file" required />
<input type="file" id="file" name="file" />
</div>
<div class="form-group">
<label for="fileContents">or copy/paste the import file contents</label>
<textarea id="fileContents" class="form-control" name="fileContents" ng-model="model.fileContents"
style="height: 150px;"></textarea>
</div>
</div>
<div class="modal-footer">

View File

@@ -1,56 +1,177 @@
<section class="content-header">
<h1>
My Vault
<small>{{folders.length > 0 ? folders.length - 1 : 0}} folders, {{logins.length}} logins</small>
<small>
<span ng-pluralize
count="vaultFolders.length > 0 ? vaultFolders.length - 1 : 0"
when="{'1': '{} folder', 'other': '{} folders'}"></span>,
<span ng-pluralize count="logins.length" when="{'1': '{} login', 'other': '{} logins'}"></span>
</small>
</h1>
</section>
<section class="content">
<div ng-show="loadingFolders && !folders.length">
<div ng-show="loading && !vaultFolders.length">
<p>Loading...</p>
</div>
<div class="box" ng-repeat="folder in folders | orderBy: folderSort" ng-show="folders.length && (!main.searchVaultText || folderLogins.length)">
<div class="box box-primary" ng-class="{'collapsed-box': favoriteCollapsed}" style="margin-bottom: 40px;"
ng-show="vaultFolders.length && (!main.searchVaultText || favoriteLogins.length)">
<div class="box-header with-border">
<h3 class="box-title"><i class="fa fa-folder-open"></i> {{folder.name}} <small>{{folderLogins.length}} logins</small></h3>
<div class="box-tools pull-right">
<button type="button" class="btn btn-box-tool" ng-click="addLogin(folder)" uib-tooltip="Add Login">
<i class="fa fa-plus"></i>
<h3 class="box-title">
<i class="fa fa-star"></i>
Favorites
<small ng-pluralize count="favoriteLogins.length" when="{'1': '{} login', 'other': '{} logins'}"></small>
</h3>
<div class="box-tools">
<div class="btn-group">
<button type="button" class="btn btn-box-tool dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu dropdown-menu-right">
<li>
<a href="#" ng-click="addLogin(null, true)">
<i class="fa fa-fw fa-plus-circle"></i> Add Login
</a>
</li>
</ul>
</div>
<button type="button" class="btn btn-box-tool" data-widget="collapse" title="Collapse/Expand"
ng-click="collapseExpand(null, true)">
<i class="fa" ng-class="{'fa-minus': !favoriteCollapsed, 'fa-plus': favoriteCollapsed}"></i>
</button>
<button type="button" class="btn btn-box-tool" ng-click="deleteFolder(folder)" ng-show="canDeleteFolder(folder)" uib-tooltip="Delete">
<i class="fa fa-trash"></i>
</button>
<button type="button" class="btn btn-box-tool" ng-click="editFolder(folder)" ng-show="folder.id" uib-tooltip="Edit">
<i class="fa fa-pencil"></i>
</button>
<button type="button" class="btn btn-box-tool" data-widget="collapse" uib-tooltip="Collapse/Expand">
<i class="fa fa-minus"></i>
</div>
</div>
<div class="box-body" ng-class="{'no-padding': favoriteLogins.length}">
<div ng-show="!favoriteLogins.length">
<p>No favorite logins.</p>
<button type="button" ng-click="addLogin(null, true)" class="btn btn-default btn-flat">Add a Login</button>
</div>
<div class="table-responsive" ng-show="favoriteLogins.length">
<table class="table table-striped table-hover table-vmiddle">
<tbody>
<tr ng-repeat="login in favoriteLogins = (logins | filter: { favorite: true } |
filter: (main.searchVaultText || '')) track by login.id">
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="editLogin(login)">
<i class="fa fa-fw fa-pencil"></i> Edit
</a>
</li>
<li ng-show="!login.organizationId">
<a href="javascript:void(0)" ng-click="share(login)">
<i class="fa fa-fw fa-share-alt"></i> Share
</a>
</li>
<li ng-show="login.organizationId">
<a href="javascript:void(0)" ng-click="collections(login)">
<i class="fa fa-fw fa-cubes"></i> Collections
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="deleteLogin(login)" class="text-red">
<i class="fa fa-fw fa-trash"></i> Delete
</a>
</li>
</ul>
</div>
</td>
<td>
<a href="javascript:void(0)" ng-click="editLogin(login)">{{login.name}}</a>
<i class="fa fa-share-alt text-muted" title="Shared" ng-show="login.organizationId"></i>
<div class="text-sm text-muted">{{login.username}}</div>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<div class="box" ng-class="{'collapsed-box': folder.collapsed}" ng-repeat="folder in vaultFolders track by folder.id"
ng-show="vaultFolders.length && (!main.searchVaultText || folderLogins.length)">
<div class="box-header with-border">
<h3 class="box-title">
<i class="fa" ng-class="{'fa-folder-open': folder.id !== null, 'fa-folder-open-o': folder.id === null}"></i>
{{folder.name}}
<small ng-pluralize count="folderLogins.length" when="{'1': '{} login', 'other': '{} logins'}"></small>
</h3>
<div class="box-tools">
<div class="btn-group">
<button type="button" class="btn btn-box-tool dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu dropdown-menu-right">
<li>
<a href="#" ng-click="addLogin(folder)">
<i class="fa fa-fw fa-plus-circle"></i> Add Login
</a>
</li>
<li ng-show="folder.id">
<a href="#" ng-click="editFolder(folder)">
<i class="fa fa-fw fa-pencil"></i> Edit Folder
</a>
</li>
<li ng-show="canDeleteFolder(folder)">
<a href="#" ng-click="deleteFolder(folder)" class="text-red">
<i class="fa fa-fw fa-trash"></i> Delete Folder
</a>
</li>
</ul>
</div>
<button type="button" class="btn btn-box-tool" data-widget="collapse" title="Collapse/Expand"
ng-click="collapseExpand(folder)">
<i class="fa" ng-class="{'fa-minus': !folder.collapsed, 'fa-plus': folder.collapsed}"></i>
</button>
</div>
</div>
<div class="box-body" ng-class="{'no-padding': folderLogins.length}">
<div ng-show="loadingLogins && !folderLogins.length">
<p>Loading logins...</p>
</div>
<div ng-show="!loadingLogins && !folderLogins.length">
<div ng-show="!folderLogins.length">
<p>No logins in this folder.</p>
<button type="button" ng-click="addLogin(folder)" class="btn btn-default btn-flat">Add a Login</button>
</div>
<div class="table-responsive" ng-show="folderLogins.length">
<table class="table table-striped table-hover">
<thead>
<tr>
<th style="width: 75px; min-width: 75px;"></th>
<th>Name</th>
<th style="width: 300px;">Username</th>
</tr>
</thead>
<table class="table table-striped table-hover table-vmiddle">
<tbody>
<tr ng-repeat="login in folderLogins = (logins | filter: { folderId: folder.id } | filter: (main.searchVaultText || '') | orderBy: ['name', 'username'])">
<td>
<button type="button" ng-click="deleteLogin(login)" class="btn btn-link btn-table" uib-tooltip="Delete"><i class="fa fa-lg fa-trash"></i></button>
<button type="button" ng-click="editLogin(login)" class="btn btn-link btn-table" uib-tooltip="View/Edit"><i class="fa fa-lg fa-pencil"></i></button>
<tr ng-repeat="login in folderLogins = (logins | filter: { folderId: folder.id } |
filter: (main.searchVaultText || '')) track by login.id">
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="editLogin(login)">
<i class="fa fa-fw fa-pencil"></i> Edit
</a>
</li>
<li ng-show="!login.organizationId">
<a href="javascript:void(0)" ng-click="share(login)">
<i class="fa fa-fw fa-share-alt"></i> Share
</a>
</li>
<li ng-show="login.organizationId">
<a href="javascript:void(0)" ng-click="collections(login)">
<i class="fa fa-fw fa-cubes"></i> Collections
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="deleteLogin(login)" class="text-red">
<i class="fa fa-fw fa-trash"></i> Delete
</a>
</li>
</ul>
</div>
</td>
<td>
<a href="javascript:void(0)" ng-click="editLogin(login)">{{login.name}}</a>
<i class="fa fa-star text-muted" title="Favorite" ng-show="login.favorite"></i>
<i class="fa fa-share-alt text-muted" title="Shared" ng-show="login.organizationId"></i>
<div class="text-sm text-muted">{{login.username}}</div>
</td>
<td>{{login.name}} <i class="fa fa-star text-muted" uib-tooltip="Favorite" ng-show="login.favorite"></i></td>
<td>{{login.username}}</td>
</tr>
</tbody>
</table>

View File

@@ -17,7 +17,7 @@
<input type="text" id="name" name="Name" ng-model="login.name" class="form-control" required api-field />
</div>
</div>
<div class="col-md-6">
<div class="col-md-6" ng-if="!hideFolders">
<div class="form-group" show-errors>
<label for="folder">Folder</label>
<select id="folder" name="FolderId" ng-model="login.folderId" class="form-control" api-field>
@@ -82,7 +82,7 @@
<label for="notes">Notes</label>
<textarea id="notes" name="Notes" class="form-control" ng-model="login.notes" api-field></textarea>
</div>
<div class="checkbox">
<div class="checkbox" ng-if="!hideFavorite">
<label>
<input type="checkbox" ng-model="login.favorite" name="Favorite" />
Favorite

View File

@@ -1,6 +1,8 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title" id="editLoginModelLabel"><i class="fa fa-globe"></i> Login Information <small>{{login.name}}</small></h4>
<h4 class="modal-title" id="editLoginModelLabel">
<i class="fa fa-globe"></i> Login Information <small>{{login.name}}</small>
</h4>
</div>
<form name="editLoginForm" ng-submit="editLoginForm.$valid && save(login)" api-form="savePromise">
<div class="modal-body">
@@ -14,14 +16,17 @@
<div class="col-md-6">
<div class="form-group" show-errors>
<label for="name">Name</label> <span>*</span>
<input type="text" id="name" name="Name" ng-model="login.name" class="form-control" required api-field />
<input type="text" id="name" name="Name" ng-model="login.name" class="form-control"
ng-readonly="readOnly" required api-field />
</div>
</div>
<div class="col-md-6">
<div class="col-md-6" ng-if="!hideFolders">
<div class="form-group" show-errors>
<label for="folder">Folder</label>
<select id="folder" name="FolderId" ng-model="login.folderId" class="form-control" api-field>
<option ng-repeat="folder in folders | orderBy: folderSort" value="{{folder.id}}">{{folder.name}}</option>
<option ng-repeat="folder in folders | orderBy: folderSort" value="{{folder.id}}">
{{folder.name}}
</option>
</select>
</div>
</div>
@@ -29,14 +34,16 @@
<div class="form-group" show-errors>
<label for="uri">URI</label>
<div class="input-group">
<input type="text" id="uri" name="Uri" ng-model="login.uri" class="form-control" placeholder="http://..." api-field />
<input type="text" id="uri" name="Uri" ng-model="login.uri" class="form-control" placeholder="http://..."
ng-readonly="readOnly" api-field />
<span class="input-group-btn">
<button tabindex="-1" class="btn btn-default btn-flat" type="button" uib-tooltip="Copy URI" tooltip-placement="left" ngclipboard
ngclipboard-error="clipboardError(e)"
<button class="btn btn-default btn-flat" type="button" uib-tooltip="Copy URI"
tooltip-placement="left" ngclipboard ngclipboard-error="clipboardError(e)"
data-clipboard-target="#uri">
<i class="fa fa-clipboard"></i>
</button>
<a href="{{login.uri}}" target="_blank" class="btn btn-default btn-flat" uib-tooltip="Go To Login" tooltip-placement="left">
<a href="{{login.uri}}" target="_blank" class="btn btn-default btn-flat" uib-tooltip="Go To Login"
tooltip-placement="left">
<i class="fa fa-share"></i>
</a>
</span>
@@ -47,9 +54,10 @@
<div class="form-group" show-errors>
<label for="username">Username</label>
<div class="input-group">
<input type="text" id="username" name="Username" ng-model="login.username" class="form-control" api-field />
<input type="text" id="username" name="Username" ng-model="login.username" class="form-control"
ng-readonly="readOnly" api-field />
<span class="input-group-btn" uib-tooltip="Copy Username" tooltip-placement="left">
<button tabindex="-1" class="btn btn-default btn-flat" type="button" ngclipboard
<button class="btn btn-default btn-flat" type="button" ngclipboard
ngclipboard-error="clipboardError(e)"
data-clipboard-target="#username">
<i class="fa fa-clipboard"></i>
@@ -61,31 +69,34 @@
<div class="col-md-6">
<div class="form-group" show-errors>
<div class="pull-right password-options">
<i class="fa fa-lg fa-refresh" uib-tooltip="Generate Password" tooltip-placement="left" ng-click="generatePassword()"></i>
<i class="fa fa-lg fa-eye" uib-tooltip="Toggle Password" tooltip-placement="left" password-viewer="#password"></i>
<i class="fa fa-lg fa-refresh" uib-tooltip="Generate Password" tooltip-placement="left"
ng-click="generatePassword()" ng-show="!readOnly"></i>
<i class="fa fa-lg fa-eye" uib-tooltip="Toggle Password" tooltip-placement="left"
password-viewer="#password"></i>
</div>
<label for="password">Password</label>
<div class="input-group">
<input type="text" id="password-text" value="{{login.password}}" style="margin-left: -9999px;" />
<input type="password" id="password" name="Password" ng-model="login.password" class="form-control" api-field />
<input type="password" id="password" name="Password" ng-model="login.password" class="form-control"
ng-readonly="readOnly" api-field />
<span class="input-group-btn" uib-tooltip="Copy Password" tooltip-placement="left">
<button tabindex="-1" class="btn btn-default btn-flat" type="button" ngclipboard
ngclipboard-success="clipboardSuccess(e)"
ngclipboard-error="clipboardError(e, true)"
data-clipboard-target="#password-text">
<button class="btn btn-default btn-flat" type="button" ngclipboard
ngclipboard-success="clipboardSuccess(e)" ngclipboard-error="clipboardError(e, true)"
data-clipboard-text="{{login.password}}">
<i class="fa fa-clipboard"></i>
</button>
</span>
</div>
</div>
<div style="margin: -10px 0 15px 0;" password-meter="login.password" password-meter-username="login.username" outer-class="xs"></div>
<div style="margin: -10px 0 15px 0;" password-meter="login.password" password-meter-username="login.username"
outer-class="xs"></div>
</div>
</div>
<div class="form-group" show-errors>
<label for="notes">Notes</label>
<textarea id="notes" name="Notes" class="form-control" ng-model="login.notes" api-field></textarea>
<textarea id="notes" name="Notes" class="form-control" ng-model="login.notes"
ng-readonly="readOnly" api-field></textarea>
</div>
<div class="checkbox">
<div class="checkbox" ng-if="!hideFavorite">
<label>
<input type="checkbox" ng-model="login.favorite" name="Favorite" />
Favorite
@@ -97,7 +108,7 @@
<i class="fa fa-refresh fa-spin loading-icon" ng-show="editLoginForm.$loading"></i>Save
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
<button type="button" class="btn btn-link pull-right" ng-click="delete()" uib-tooltip="Delete">
<button type="button" class="btn btn-link pull-right" ng-click="delete()" uib-tooltip="Delete" ng-disabled="readOnly">
<i class="fa fa-trash fa-lg"></i>
</button>
</div>

View File

@@ -0,0 +1,55 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-cubes"></i> Collections <small>{{login.name}}</small></h4>
</div>
<form name="form" ng-submit="form.$valid && submit()" api-form="submitPromise">
<div class="modal-body">
<p>Edit the collections that this login is being shared with.</p>
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<div ng-show="loadingCollections && !collections.length">
Loading...
</div>
<div ng-show="!loadingCollections && !collections.length" class="callout callout-default">
<p>No collections to manage.</p>
</div>
<div class="table-responsive" ng-show="collections.length" style="margin: 0;">
<table class="table table-striped table-hover" style="margin: 0;">
<thead>
<tr>
<th style="width: 40px;">
<input type="checkbox"
ng-checked="allSelected()"
ng-click="toggleCollectionSelectionAll($event)">
</th>
<th>Name</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="collection in collections | orderBy: ['name']">
<td valign="middle">
<input type="checkbox"
name="selectedCollections[]"
value="{{collection.id}}"
ng-checked="collectionSelected(collection)"
ng-click="toggleCollectionSelection(collection.id)">
</td>
<td valign="middle" ng-click="toggleCollectionSelection(collection.id)">
{{collection.name}}
</td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading" ng-show="collections.length">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Save
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,75 @@
<div class="modal-header">
<button type="button" class="close" ng-click="close()" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title"><i class="fa fa-share-alt"></i> Share Login <small>{{login.name}}</small></h4>
</div>
<form name="form" ng-submit="form.$valid && submit(model)" api-form="submitPromise">
<div class="modal-body">
<p>Choose an organization that you wish to share this login with.</p>
<div class="callout callout-danger validation-errors" ng-show="form.$errors">
<h4>Errors have occured</h4>
<ul>
<li ng-repeat="e in form.$errors">{{e}}</li>
</ul>
</div>
<p ng-show="loading">Loading...</p>
<div ng-show="!loading && !organizations.length" class="callout callout-default">
<h4><i class="fa fa-info-circle"></i> No Organizations</h4>
<p>You do not belong to any organizations. Organizations allow you to share logins with other bitwarden users.</p>
<a ng-click="createOrg()" class="btn btn-default btn-flat">
Create an Organization
</a>
</div>
<div ng-show="!loading && organizations.length">
<div class="form-group">
<label for="organization">Organization</label> <span>*</span>
<select id="organization" name="Organization" ng-model="model.organizationId" class="form-control"
ng-change="orgChanged()">
<option ng-repeat="org in organizations | orderBy: ['name']" value="{{org.id}}">{{org.name}}</option>
</select>
</div>
<h4 ng-hide="!loadingCollections && !orgCollections.length">Collection Access</h4>
<div ng-show="loadingCollections && !orgCollections.length">
<p>Loading...</p>
</div>
<div ng-show="!loadingCollections && !orgCollections.length" class="callout callout-default">
<h4><i class="fa fa-info-circle"></i> No Collections</h4>
<p>You do not have write access to any collections for this organization.</p>
</div>
<div class="table-responsive" ng-show="orgCollections.length" style="margin: 0;">
<table class="table table-striped table-hover" style="margin: 0;">
<thead>
<tr>
<th style="width: 40px;">
<input type="checkbox"
ng-checked="allSelected()"
ng-click="toggleCollectionSelectionAll($event)">
</th>
<th>Name</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="collection in orgCollections =
(collections | filter: { organizationId: model.organizationId } | orderBy: ['name'])">
<td valign="middle">
<input type="checkbox"
name="selectedCollections[]"
value="{{collection.id}}"
ng-checked="collectionSelected(collection)"
ng-click="toggleCollectionSelection(collection.id)">
</td>
<td valign="middle" ng-click="toggleCollectionSelection(collection.id)">
{{collection.name}}
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<div class="modal-footer">
<button type="submit" class="btn btn-primary btn-flat" ng-disabled="form.$loading">
<i class="fa fa-refresh fa-spin loading-icon" ng-show="form.$loading"></i>Save
</button>
<button type="button" class="btn btn-default btn-flat" ng-click="close()">Close</button>
</div>
</form>

View File

@@ -0,0 +1,90 @@
<section class="content-header">
<h1>
Shared
<small>
<span ng-pluralize
count="collections.length > 0 && logins.length ? collections.length - 1 : collections.length"
when="{'1': '{} collection', 'other': '{} collections'}"></span>,
<span ng-pluralize count="logins.length" when="{'1': '{} login', 'other': '{} logins'}"></span>
</small>
</h1>
</section>
<section class="content">
<p ng-show="loading && !collections.length">Loading...</p>
<div class="callout callout-default" style="background: #fff;" ng-show="!loading && !collections.length && !logins.length">
<h4>Nothing shared <i class="fa fa-frown-o"></i></h4>
<p>
You do not have any logins or collections being shared with you.
To start sharing, create an organization or ask an existing organization to invite you.
</p>
<a ui-sref="backend.user.settingsCreateOrg" class="btn btn-default btn-flat">
Create an Organization
</a>
</div>
<div class="box" ng-class="{'collapsed-box': collection.collapsed}" ng-repeat="collection in collections |
orderBy: collectionSort track by collection.id"
ng-show="collections.length">
<div class="box-header with-border">
<h3 class="box-title">
<i class="fa" ng-class="{'fa-cubes': collection.id, 'fa-sitemap': !collection.id}"></i>
{{collection.name}}
<small ng-pluralize count="collectionLogins.length" when="{'1': '{} login', 'other': '{} logins'}"></small>
</h3>
<div class="box-tools">
<button type="button" class="btn btn-box-tool" data-widget="collapse" title="Collapse/Expand"
ng-click="collapseExpand(collection)">
<i class="fa" ng-class="{'fa-minus': !collection.collapsed, 'fa-plus': collection.collapsed}"></i>
</button>
</div>
</div>
<div class="box-body" ng-class="{'no-padding': collectionLogins.length}">
<div ng-show="!collectionLogins.length && collection.id">
<p>No logins in this collection.</p>
<p>
Share a login to this collection by selecting <i class="fa fa-share-alt"></i> <b>Share</b> or
<i class="fa fa-cubes"></i> <b>Collections</b> from the login's options (<i class="fa fa-cog"></i>) menu.
</p>
</div>
<div ng-show="!collectionLogins.length && !collection.id">No unassigned logins.</div>
<div class="table-responsive" ng-show="collectionLogins.length">
<table class="table table-striped table-hover table-vmiddle">
<tbody>
<tr ng-repeat="login in collectionLogins = (logins | filter: filterByCollection(collection) |
orderBy: ['name', 'username']) track by login.id">
<td style="width: 70px;">
<div class="btn-group" data-append-to="body">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">
<i class="fa fa-cog"></i> <span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<a href="javascript:void(0)" ng-click="editLogin(login)">
<i class="fa fa-fw fa-pencil"></i> Edit
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="editCollections(login)">
<i class="fa fa-fw fa-cubes"></i> Collections
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="removeLogin(login, collection)"
ng-if="collection.id" class="text-red">
<i class="fa fa-fw fa-remove"></i> Remove
</a>
</li>
</ul>
</div>
</td>
<td>
<a href="javascript:void(0)" ng-click="editLogin(login)">{{login.name}}</a>
<i class="fa fa-star text-muted" title="Favorite" ng-show="login.favorite"></i>
<div class="text-sm text-muted">{{login.username}}</div>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</section>

141
app/views/apps.html Normal file
View File

@@ -0,0 +1,141 @@
<section class="content-header">
<h1>
Apps
<small>for all of your devices</small>
</h1>
</section>
<section class="content">
<div class="box box-default box-apps">
<div class="box-header with-border">
<h3 class="box-title">Desktop/Browser</h3>
</div>
<div class="box-body">
<div class="row">
<div class="col-sm-6">
<ul class="fa-ul">
<li>
<a href="https://chrome.google.com/webstore/detail/bitwarden-free-password-m/nngceckbapebfimnlniiiahkandclblb" target="_blank">
<i class="fa fa-chrome fa-lg fa-fw fa-li"></i> Chrome
</a>
</li>
<li>
<a href="https://addons.mozilla.org/firefox/addon/bitwarden-password-manager/" target="_blank">
<i class="fa fa-firefox fa-lg fa-fw fa-li"></i> Firefox
</a>
</li>
<li>
<a href="https://addons.opera.com/extensions/details/bitwarden-free-password-manager/" target="_blank">
<i class="fa fa-opera fa-lg fa-fw fa-li"></i> Opera
</a>
</li>
<li>
<a href="javascript:void(0)">
<i class="fa fa-edge fa-lg fa-fw fa-li"></i> Edge
<small class="text-muted">(coming soon)</small>
</a>
</li>
</ul>
</div>
<div class="col-sm-6">
Others:
<ul>
<li>
<a href="https://chrome.google.com/webstore/detail/bitwarden-free-password-m/nngceckbapebfimnlniiiahkandclblb" target="_blank">
Vivaldi
</a>
</li>
<li>
<a href="https://brave.com/" target="_blank">
Brave
</a>
</li>
<li>
<a href="https://addons.mozilla.org/firefox/addon/bitwarden-password-manager/" target="_blank">
Tor
</a>
</li>
</ul>
</div>
</div>
</div>
</div>
<div class="box box-default box-apps">
<div class="box-header with-border">
<h3 class="box-title">Mobile</h3>
</div>
<div class="box-body">
<div class="row">
<div class="col-sm-6">
<ul class="fa-ul">
<li>
<a href="https://itunes.apple.com/app/bitwarden-free-password-manager/id1137397744?mt=8" target="_blank">
<i class="fa fa-apple fa-lg fa-fw fa-li"></i> iOS
</a>
</li>
<li>
<a href="https://play.google.com/store/apps/details?id=com.x8bit.bitwarden" target="_blank">
<i class="fa fa-android fa-lg fa-fw fa-li"></i> Android
</a>
</li>
</ul>
</div>
<div class="col-sm-6">
<ul class="fa-ul">
<li>
<a href="https://www.amazon.com/dp/B06XMYGPMV" target="_blank">
<i class="fa fa-amazon fa-lg fa-fw fa-li"></i> Amazon
</a>
</li>
<li>
<a href="javascript:void(0)">
<i class="fa fa-windows fa-lg fa-fw fa-li"></i> Windows
<small class="text-muted">(coming soon)</small>
</a>
</li>
</ul>
</div>
</div>
</div>
</div>
<div class="box box-default box-apps">
<div class="box-header with-border">
<h3 class="box-title">Other</h3>
</div>
<div class="box-body">
<div class="row">
<div class="col-sm-6">
<ul class="fa-ul">
<li>
<a href="javascript:void(0)">
<i class="fa fa-windows fa-lg fa-fw fa-li"></i> Desktop Windows
<small class="text-muted">(coming soon)</small>
</a>
</li>
<li>
<a href="javascript:void(0)">
<i class="fa fa-apple fa-lg fa-fw fa-li"></i> Desktop macOS
<small class="text-muted">(coming soon)</small>
</a>
</li>
</ul>
</div>
<div class="col-sm-6">
<ul class="fa-ul">
<li>
<a href="javascript:void(0)">
<i class="fa fa-linux fa-lg fa-fw fa-li"></i> Desktop Linux
<small class="text-muted">(coming soon)</small>
</a>
</li>
<li>
<a href="javascript:void(0)">
<i class="fa fa-terminal fa-lg fa-fw fa-li"></i> CLI
<small class="text-muted">(coming soon)</small>
</a>
</li>
</ul>
</div>
</div>
</div>
</div>
</section>

View File

@@ -1,137 +1,10 @@
<div class="wrapper toast-target">
<header class="main-header" ng-controller="topNavController as topNav">
<a ui-sref="backend.vault" class="logo">
<span class="logo-mini"><i class="fa fa-shield"></i></span>
<span class="logo-lg"><i class="fa fa-shield"></i> <b>bit</b>warden</span>
</a>
<nav class="navbar navbar-static-top" role="navigation">
<a class="sidebar-toggle" data-toggle="offcanvas" role="button">
<span class="sr-only">Toggle navigation</span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</a>
<div class="navbar-custom-menu">
<ul class="nav navbar-nav">
<li><a ui-sref="frontend.logout">Log Out</a></li>
</ul>
</div>
</nav>
</header>
<aside class="main-sidebar" ng-controller="sideNavController as sideNav">
<section class="sidebar">
<div class="user-panel">
<div class="pull-left image">
<img src="//www.gravatar.com/avatar/{{ main.userProfile.email | gravatar }}.jpg?s=45&d=mm"
class="img-circle" alt="User Image">
</div>
<div class="pull-left info">
<p>{{main.userProfile.extended && main.userProfile.extended.name ? main.userProfile.extended.name : main.userProfile.email}}</p>
<a ui-sref="frontend.logout">Log Out</a>
</div>
</div>
<form class="sidebar-form">
<label for="search" class="sr-only">Search</label>
<div class="form-group has-feedback">
<input type="text" id="search" class="form-control" placeholder="Search vault..."
ng-focus="searchVault()" ng-model="main.searchVaultText" />
<span class="fa fa-search form-control-feedback" aria-hidden="true"></span>
</div>
</form>
<ul class="sidebar-menu">
<li class="header">WEB VAULT</li>
<li class="treeview" ng-class="{active: $state.includes('backend.vault')}">
<a ui-sref="backend.vault"><i class="fa fa-lock"></i> <span>My Vault</span></a>
<ul class="treeview-menu menu-open">
<li>
<a href="javascript:void(0)" ng-click="addLogin()">
<i class="fa fa-plus"></i> New Login
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="addFolder()">
<i class="fa fa-folder"></i> New Folder
</a>
</li>
</ul>
</li>
<li class="treeview"
ng-class="{active: $state.includes('backend.settings') || $state.includes('backend.settingsDomains')}">
<a ui-sref="backend.settings"><i class="fa fa-cogs"></i> <span>Settings</span></a>
<ul class="treeview-menu">
<li>
<a ui-sref="backend.settingsDomains">
<i class="fa fa-circle-o"></i> Domain Rules
</a>
</li>
</ul>
</li>
<li class="treeview" ng-class="{active: $state.includes('backend.tools')}">
<a ui-sref="backend.tools"><i class="fa fa-wrench"></i> <span>Tools</span></a>
</li>
<li>
<a href="https://help.bitwarden.com/" target="_blank"
analytics-on="click" analytics-event="Clicked Get Help">
<i class="fa fa-info-circle"></i> <span>Get Help</span>
</a>
</li>
<li class="header">
<small class="label pull-right bg-green">FREE</small>
MOBILE APPS
</li>
<li>
<a href="https://itunes.apple.com/us/app/bitwarden-free-password-manager/id1137397744?mt=8"
target="_blank" analytics-on="click" analytics-event="Clicked iOS">
<i class="fa fa-apple"></i> <span>iOS</span>
</a>
</li>
<li>
<a href="https://play.google.com/store/apps/details?id=com.x8bit.bitwarden"
target="_blank" analytics-on="click" analytics-event="Clicked Android">
<i class="fa fa-android"></i> <span>Android</span>
</a>
</li>
<li class="header">
<small class="label pull-right bg-green">FREE</small>
BROWSER EXTENSIONS
</li>
<li>
<a href="https://chrome.google.com/webstore/detail/bitwarden-free-password-m/nngceckbapebfimnlniiiahkandclblb"
target="_blank" analytics-on="click" analytics-event="Clicked Chrome">
<i class="fa fa-chrome"></i> <span>Chrome</span>
</a>
</li>
<li>
<a href="https://addons.mozilla.org/firefox/addon/bitwarden-password-manager/"
target="_blank" analytics-on="click" analytics-event="Clicked Firefox">
<i class="fa fa-firefox"></i> <span>Firefox</span>
</a>
</li>
<li>
<a href="https://addons.opera.com/extensions/details/bitwarden-free-password-manager/"
target="_blank" analytics-on="click" analytics-event="Clicked Opera">
<i class="fa fa-opera"></i> <span>Opera</span>
</a>
</li>
<li>
<a href="javascript:void(0)"
target="_blank" analytics-on="click" analytics-event="Clicked Edge">
<small class="label pull-right bg-gray">coming soon</small>
<i class="fa fa-edge"></i> <span>Edge</span>
</a>
</li>
</ul>
</section>
</aside>
<div class="content-wrapper" ui-view>
</div>
<div ui-view></div>
<footer class="main-footer">
<div class="pull-right hidden-xs">
<b>Version</b> {{main.version}}
</div>
<strong>Copyright &copy; <span ng-bind="currentYear"></span></strong>, bitwarden.com
<strong>Copyright &copy; <span ng-bind="currentYear"></span></strong>, 8bit Solutions LLC
</footer>
</div>

View File

@@ -0,0 +1,103 @@
<header class="main-header" ng-controller="topNavController as topNav">
<a ui-sref="backend.user.vault" class="logo">
<span class="logo-mini"><i class="fa fa-shield"></i></span>
<span class="logo-lg"><i class="fa fa-shield"></i> <b>bit</b>warden</span>
</a>
<nav class="navbar navbar-static-top" role="navigation">
<a class="sidebar-toggle" data-toggle="offcanvas" role="button">
<span class="sr-only">Toggle navigation</span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</a>
<div class="navbar-custom-menu">
<ul class="nav navbar-nav">
<li><a ui-sref="frontend.logout">Log Out</a></li>
</ul>
</div>
</nav>
</header>
<aside class="main-sidebar" ng-controller="sideNavController">
<section class="sidebar">
<div class="user-panel">
<div class="pull-left image">
<letter-avatar data="{{orgProfile.name}}" avclass="img-responsive img-rounded" round="false"></letter-avatar>
</div>
<div class="pull-left info">
<p>{{orgProfile.name}}</p>
<a ui-sref="backend.user.vault"><i class="fa fa-arrow-left"></i> Return to my vault</a>
</div>
</div>
<form class="sidebar-form">
<label for="search" class="sr-only">Search</label>
<div class="form-group has-feedback">
<input type="text" id="search" class="form-control" placeholder="Search org. vault..."
ng-focus="searchOrganizationVault()" ng-model="main.searchVaultText" />
<span class="fa fa-search form-control-feedback" aria-hidden="true"></span>
</div>
</form>
<ul class="sidebar-menu">
<li class="header">MY ORGANIZATION</li>
<li ng-class="{active: $state.is('backend.org.dashboard')}">
<a ui-sref="backend.org.dashboard({orgId: params.orgId})">
<i class="fa fa-dashboard fa-fw"></i> <span>Dashboard</span>
</a>
</li>
<li ng-class="{active: $state.is('backend.org.vault')}">
<a ui-sref="backend.org.vault({orgId: params.orgId})">
<i class="fa fa-lock fa-fw"></i> <span>Vault</span>
</a>
<ul class="treeview-menu" ng-class="{'menu-open': $state.includes('backend.org.vault')}">
<li>
<a href="javascript:void(0)" ng-click="addOrganizationLogin()">
<i class="fa fa-plus-circle fa-fw"></i> New Login
</a>
</li>
</ul>
</li>
<li ng-class="{active: $state.is('backend.org.collections')}">
<a ui-sref="backend.org.collections({orgId: params.orgId})">
<i class="fa fa-cubes fa-fw"></i> <span>Collections</span>
</a>
<ul class="treeview-menu" ng-class="{'menu-open': $state.includes('backend.org.collections')}">
<li>
<a href="javascript:void(0)" ng-click="addOrganizationCollection()">
<i class="fa fa-plus-circle fa-fw"></i> New Collection
</a>
</li>
</ul>
</li>
<li ng-class="{active: $state.is('backend.org.people')}">
<a ui-sref="backend.org.people({orgId: params.orgId})">
<i class="fa fa-users fa-fw"></i> <span>People</span>
</a>
<ul class="treeview-menu" ng-class="{'menu-open': $state.includes('backend.org.people')}">
<li>
<a href="javascript:void(0)" ng-click="inviteOrganizationUser()">
<i class="fa fa-plus-circle fa-fw"></i> Invite a User
</a>
</li>
</ul>
</li>
<li ng-class="{active: $state.is('backend.org.groups')}">
<a ui-sref="backend.org.groups({orgId: params.orgId})">
<i class="fa fa-sitemap fa-fw"></i> <span>Groups</span>
</a>
</li>
<li ng-class="{active: $state.is('backend.org.billing')}" ng-if="isOrgOwner(orgProfile)">
<a ui-sref="backend.org.billing({orgId: params.orgId})">
<i class="fa fa-credit-card fa-fw"></i> <span>Billing</span>
</a>
</li>
<li ng-class="{active: $state.is('backend.org.settings')}" ng-if="isOrgOwner(orgProfile)">
<a ui-sref="backend.org.settings({orgId: params.orgId})">
<i class="fa fa-gears fa-fw"></i> <span>Settings</span>
</a>
</li>
</ul>
</section>
</aside>
<div class="content-wrapper" ui-view>
</div>

122
app/views/userLayout.html Normal file
View File

@@ -0,0 +1,122 @@
<header class="main-header" ng-controller="topNavController as topNav">
<a ui-sref="backend.user.vault" class="logo">
<span class="logo-mini"><i class="fa fa-shield"></i></span>
<span class="logo-lg"><i class="fa fa-shield"></i> <b>bit</b>warden</span>
</a>
<nav class="navbar navbar-static-top" role="navigation">
<a class="sidebar-toggle" data-toggle="offcanvas" role="button">
<span class="sr-only">Toggle navigation</span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</a>
<div class="navbar-custom-menu">
<ul class="nav navbar-nav">
<li><a ui-sref="frontend.logout">Log Out</a></li>
</ul>
</div>
</nav>
</header>
<aside class="main-sidebar" ng-controller="sideNavController as sideNav">
<section class="sidebar">
<div class="user-panel">
<div class="pull-left image">
<letter-avatar data="{{name}}" avclass="img-responsive"></letter-avatar>
</div>
<div class="pull-left info">
<p>{{name}}</p>
<a ui-sref="frontend.logout">Log Out</a>
</div>
</div>
<form class="sidebar-form">
<label for="search" class="sr-only">Search</label>
<div class="form-group has-feedback">
<input type="text" id="search" class="form-control" placeholder="Search my vault..."
ng-focus="searchVault()" ng-model="main.searchVaultText" />
<span class="fa fa-search form-control-feedback" aria-hidden="true"></span>
</div>
</form>
<ul class="sidebar-menu">
<li class="header">WEB VAULT</li>
<li class="treeview" ng-class="{active: $state.includes('backend.user.vault')}">
<a ui-sref="backend.user.vault"><i class="fa fa-lock fa-fw"></i> <span>My Vault</span></a>
<ul class="treeview-menu" ng-class="{'menu-open': $state.includes('backend.user.vault')}">
<li>
<a href="javascript:void(0)" ng-click="addLogin()">
<i class="fa fa-plus-circle fa-fw"></i> New Login
</a>
</li>
<li>
<a href="javascript:void(0)" ng-click="addFolder()">
<i class="fa fa-folder fa-fw"></i> New Folder
</a>
</li>
</ul>
</li>
<li class="treeview" ng-class="{active: $state.is('backend.user.shared')}">
<a ui-sref="backend.user.shared">
<small class="label pull-right bg-orange">NEW</small>
<i class="fa fa-share-alt fa-fw"></i> <span>Shared</span>
</a>
</li>
<li class="treeview" ng-class="{active: $state.is('backend.user.tools')}">
<a ui-sref="backend.user.tools"><i class="fa fa-wrench fa-fw"></i> <span>Tools</span></a>
</li>
<li class="treeview"
ng-class="{active: $state.is('backend.user.settings') || $state.is('backend.user.settingsDomains') ||
$state.is('backend.user.settingsCreateOrg')}">
<a ui-sref="backend.user.settings"><i class="fa fa-cogs fa-fw"></i> <span>Settings</span></a>
<ul class="treeview-menu" ng-class="{'menu-open': $state.is('backend.user.settings') ||
$state.is('backend.user.settingsDomains') || $state.is('backend.user.settingsCreateOrg')}">
<li ng-class="{active: $state.is('backend.user.settingsCreateOrg')}">
<a ui-sref="backend.user.settingsCreateOrg">
<i class="fa fa-plus-circle fa-fw"></i> New Organization
</a>
</li>
<li ng-class="{active: $state.is('backend.user.settingsDomains')}">
<a ui-sref="backend.user.settingsDomains">
<i class="fa fa-fw fa-circle-o"></i> Domain Rules
</a>
</li>
</ul>
</li>
<li ng-class="{active: $state.is('backend.user.apps')}">
<a ui-sref="backend.user.apps">
<small class="label pull-right bg-green">FREE</small>
<i class="fa fa-download fa-fw"></i> <span>Get the Apps</span>
</a>
</li>
<li>
<a href="https://help.bitwarden.com/" target="_blank"
analytics-on="click" analytics-event="Clicked Get Help">
<i class="fa fa-info-circle fa-fw"></i> <span>Get Help</span>
</a>
</li>
<li class="header">
ORGANIZATIONS
</li>
</ul>
<div class="subsection">
<div ng-if="!orgs.length" class="hidden-collapsed">
<p>You do not belong to any organizations.</p>
<a ui-sref="backend.user.settingsCreateOrg" class="btn btn-default btn-flat btn-block">
Create an Organization
</a>
</div>
<ul class="list-inline" ng-if="orgs.length">
<li ng-repeat="org in orgs | orderBy: ['name'] track by org.id">
<a href="javascript:void(0)" ng-click="viewOrganization(org)">
<letter-avatar data="{{org.name}}" avclass="img-responsive img-rounded" round="false"
avheight="40" avwidth="40" bgcolor="#2c3b41" avborder="true"
borderstyle="3px solid #1a2226"></letter-avatar>
</a>
</li>
</ul>
</div>
</section>
</aside>
<div class="content-wrapper" ui-view>
</div>