Compare commits
108 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| d5b0abd1ae | |||
| 81ba5bd022 | |||
| 96a3ca71a7 | |||
| a8e253553a | |||
| 91280b18f6 | |||
| fbb8ef1ba0 | |||
| 3f46d94a93 | |||
| 161fcc7f01 | |||
| 5e2cb68299 | |||
| e6a5b59ac6 | |||
| 2ffa61564c | |||
| a1d48afeca | |||
| a51e57737b | |||
| 1c8fcef754 | |||
| ab4ca0015e | |||
| f9014d649b | |||
| adf67fd89f | |||
| 805709a91b | |||
| 40a6aaa1a8 | |||
| 5e51dad445 | |||
| f2d9cc0c0b | |||
| a40f8f9a28 | |||
| 355c4184ef | |||
| 50bdd7647a | |||
| 47c85e633b | |||
| f82cda981c | |||
| aded9ec437 | |||
| bdcad7665f | |||
| 850b61fc4f | |||
| 89bb8eb3f4 | |||
| 6bc5fcad99 | |||
| 04bcf16d33 | |||
| 76752f9bd8 | |||
| 29d5d293c4 | |||
| 1ea05d8107 | |||
| 60b7347586 | |||
| b35d45bf31 | |||
| c66e9d208b | |||
| 7808a20be7 | |||
| 463ebcaa66 | |||
| 2fe55431a0 | |||
| 0a59d09d81 | |||
| 9c4d1baa52 | |||
| 7ebb26840f | |||
| ab3603318a | |||
| ac33beeba9 | |||
| 87a65f0416 | |||
| 25903c34c6 | |||
| 85b7243186 | |||
| 61cbdeb96b | |||
| 8ab087b23f | |||
| e39043af44 | |||
| 2465d4ceb8 | |||
| 8bf89fdf37 | |||
| 89f6f60c96 | |||
| 1572080976 | |||
| 03de29ebd9 | |||
| 055aea9334 | |||
| 06d31b36a6 | |||
| 440084e832 | |||
| 7abe6161d6 | |||
| 576b1bcf2e | |||
| 593d0c31fa | |||
| 09ed061c9b | |||
| 9b67f4cebf | |||
| b8571f56a6 | |||
| 55b2bcae63 | |||
| 1331c2200e | |||
| 3a27201bed | |||
| 9a03d09c04 | |||
| ad900861da | |||
| 9f127239ec | |||
| ae555f4130 | |||
| 0c25c1529d | |||
| efc11c1f40 | |||
| eabe640ebf | |||
| d9de0447f5 | |||
| 25858eb870 | |||
| dfb728655f | |||
| 614c4f2d36 | |||
| 91d3c6c717 | |||
| b235ed168a | |||
| b9d5354cc7 | |||
| 768525a0c7 | |||
| 829693c410 | |||
| a16c9f1c6c | |||
| 6242eed778 | |||
| 284ca67dd3 | |||
| 706c793cc2 | |||
| 9799071d04 | |||
| 492a3e5a8d | |||
| c6de48c8e2 | |||
| aea3c0a696 | |||
| 2fcd7f3911 | |||
| 8c6f03f257 | |||
| e3c52baf3a | |||
| 8a24fc60ca | |||
| 1beedba67d | |||
| 0cef4124db | |||
| 16233f4856 | |||
| c662620791 | |||
| 1abb97bdc7 | |||
| fe83cfa408 | |||
| 87847769ce | |||
| 49c50046c9 | |||
| c93e4d1e2d | |||
| 686e3deb6c | |||
| 916a5dc065 |
@@ -66,3 +66,4 @@ OurUmbraco.Site/App_Data/Documentation/
|
||||
OurUmbraco.Site/App_Data/NotificationTest/
|
||||
build/tools/node*
|
||||
wwwcache/
|
||||
build/toolsnode.js.*/
|
||||
|
||||
@@ -4,24 +4,24 @@
|
||||
"description": "Umbraco Our gulpjs config",
|
||||
"main": "gulpfile.js",
|
||||
"private": true,
|
||||
"dependencies": {
|
||||
},
|
||||
"dependencies": {},
|
||||
"devDependencies": {
|
||||
"gulp": "^3.9.1",
|
||||
"gulp-autoprefixer": "^3.1.0",
|
||||
"gulp-clean": "0.3.x",
|
||||
"gulp-combine-media-queries": "0.2.x",
|
||||
"gulp-concat": "2.2.x",
|
||||
"gulp-imagemin": "3.3.x",
|
||||
"gulp-jshint": "^2.0.4",
|
||||
"gulp-minify-css": "1.1.x",
|
||||
"gulp-rename": "1.2.x",
|
||||
"gulp-sass": "^2.2.0",
|
||||
"gulp-svgmin": "0.4.x",
|
||||
"gulp-uglify": "^1.5.3",
|
||||
"gulp-util": "3.0.x",
|
||||
"gulp-watch": "0.6.x",
|
||||
"gulp-minify-css": "1.1.x",
|
||||
"gulp-sass": "^2.2.0",
|
||||
"gulp-combine-media-queries": "0.2.x",
|
||||
"gulp-imagemin": "0.6.x",
|
||||
"gulp-autoprefixer": "^3.1.0",
|
||||
"gulp-uglify": "^1.5.3",
|
||||
"gulp-jshint": "2.0.0",
|
||||
"gulp-concat": "2.2.x",
|
||||
"jshint-stylish": "0.2.x",
|
||||
"gulp-clean": "0.3.x",
|
||||
"gulp-svgmin": "0.4.x",
|
||||
"gulp-rename": "1.2.x"
|
||||
"jshint": "^2.9.4",
|
||||
"jshint-stylish": "0.2.x"
|
||||
},
|
||||
"scripts": {
|
||||
"test": "gulp build --verbose"
|
||||
|
||||
@@ -62,7 +62,7 @@ function GetSearchFilters(cssClass) {
|
||||
}
|
||||
|
||||
var forumId = $('#selectCategory').val();
|
||||
if(forumId !== undefined) {
|
||||
if(forumId) {
|
||||
forumId = forumId.replace(/([A-Za-z])\w+/g, "");
|
||||
}
|
||||
|
||||
@@ -365,7 +365,8 @@ $('#search-options input[type=checkbox]').click(function () {
|
||||
newUri = updateQueryString("order", orderValue, window.location.href);
|
||||
}
|
||||
} else {
|
||||
newUri = updateQueryString(this.name, this.checked, window.location.href);
|
||||
newUri = updateQueryString(this.name, this.checked, window.location.href);
|
||||
newUri = updateQueryString("page", 1, newUri);
|
||||
}
|
||||
console.log(newUri);
|
||||
window.location = newUri;
|
||||
|
||||
@@ -1,174 +1,174 @@
|
||||
body.packages {
|
||||
nav {
|
||||
|
||||
h3 {
|
||||
&:hover {
|
||||
opacity: .8;
|
||||
}
|
||||
}
|
||||
|
||||
h4 {
|
||||
opacity: .7;
|
||||
margin: .5rem 0 .5rem;
|
||||
}
|
||||
}
|
||||
|
||||
li {
|
||||
h3 {
|
||||
opacity: .5;
|
||||
}
|
||||
|
||||
&.open, &.active {
|
||||
h3, a {
|
||||
opacity: 1;
|
||||
color: #000 !important;
|
||||
}
|
||||
}
|
||||
|
||||
&.active > ul {
|
||||
max-height: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.packages-content {
|
||||
|
||||
.search-big {
|
||||
margin-bottom: 0;
|
||||
margin-top: 20px;
|
||||
}
|
||||
|
||||
h1 {
|
||||
margin: 1em 0 10px;
|
||||
font-size: 2.1rem;
|
||||
}
|
||||
|
||||
.package {
|
||||
margin-bottom: 15px;
|
||||
padding: 20px;
|
||||
transition: all .1s linear;
|
||||
cursor: pointer;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
border-radius: 3px;
|
||||
border: 1px solid #e9e9e9;
|
||||
|
||||
&:hover {
|
||||
@include box-shadow(2);
|
||||
|
||||
.icon {
|
||||
transform: scale(1.1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.box {
|
||||
border: none;
|
||||
border-bottom: 1px solid whitesmoke;
|
||||
width: 100%;
|
||||
|
||||
body.packages {
|
||||
nav {
|
||||
|
||||
h3 {
|
||||
&:hover {
|
||||
opacity: .8;
|
||||
}
|
||||
}
|
||||
|
||||
h4 {
|
||||
opacity: .7;
|
||||
margin: .5rem 0 .5rem;
|
||||
}
|
||||
}
|
||||
|
||||
li {
|
||||
h3 {
|
||||
opacity: .5;
|
||||
}
|
||||
|
||||
&.open, &.active {
|
||||
h3, a {
|
||||
opacity: 1;
|
||||
color: #000 !important;
|
||||
}
|
||||
}
|
||||
|
||||
&.active > ul {
|
||||
max-height: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.packages-content {
|
||||
|
||||
.search-big {
|
||||
margin-bottom: 0;
|
||||
margin-top: 20px;
|
||||
}
|
||||
|
||||
h1 {
|
||||
margin: 1em 0 10px;
|
||||
font-size: 2.1rem;
|
||||
}
|
||||
|
||||
.package {
|
||||
margin-bottom: 15px;
|
||||
padding: 20px;
|
||||
transition: all .1s linear;
|
||||
cursor: pointer;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
border-radius: 3px;
|
||||
border: 1px solid #e9e9e9;
|
||||
|
||||
&:hover {
|
||||
@include box-shadow(2);
|
||||
|
||||
.icon {
|
||||
transform: scale(1.1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.box {
|
||||
border: none;
|
||||
border-bottom: 1px solid whitesmoke;
|
||||
width: 100%;
|
||||
|
||||
.row{
|
||||
width:100%;
|
||||
}
|
||||
|
||||
h3 {
|
||||
font-size: 1.1rem;
|
||||
margin-bottom: .5rem;
|
||||
font-weight: 600;
|
||||
|
||||
a {
|
||||
color: $color-headline;
|
||||
|
||||
&:hover {
|
||||
color: $color-our;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
img {
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
display: block;
|
||||
vertical-align: middle;
|
||||
|
||||
@media (min-width: $md) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
.col-xs-2 {
|
||||
vertical-align: middle !important;
|
||||
padding: 0 !important;
|
||||
}
|
||||
|
||||
.other {
|
||||
margin-top: 30px;
|
||||
}
|
||||
|
||||
.stats {
|
||||
left: calc(16.666666666666664% + 15px);
|
||||
font-family: Consolas, "Liberation Mono", Menlo, Monaco, Courier, monospace;
|
||||
font-size: .75rem;
|
||||
|
||||
i {
|
||||
margin-left: 3px;
|
||||
font-size: .9rem;
|
||||
}
|
||||
|
||||
span {
|
||||
&:first-child {
|
||||
margin-right: 0px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
p {
|
||||
font-size: .9rem;
|
||||
color: $color-text;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.package-badge {
|
||||
position: absolute;
|
||||
right: 15px;
|
||||
bottom: -3px;
|
||||
|
||||
|
||||
@media (min-width: $md) {
|
||||
position: absolute;
|
||||
right: 0;
|
||||
bottom: 25px;
|
||||
}
|
||||
}
|
||||
|
||||
.karma , .downloads {
|
||||
color: #000;
|
||||
|
||||
span {
|
||||
transform: translate(0, 2px);
|
||||
display: inline-block;
|
||||
}
|
||||
}
|
||||
|
||||
&.liked {
|
||||
.karma {
|
||||
i {
|
||||
color: $color-red;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.name {
|
||||
font-size: 1rem;
|
||||
line-height: 1.3;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.description {
|
||||
font-size: .8rem;
|
||||
margin-top: 3px;
|
||||
max-height: 28px;
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
|
||||
h3 {
|
||||
font-size: 1.1rem;
|
||||
margin-bottom: .5rem;
|
||||
font-weight: 600;
|
||||
|
||||
a {
|
||||
color: $color-headline;
|
||||
|
||||
&:hover {
|
||||
color: $color-our;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
img {
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
display: block;
|
||||
vertical-align: middle;
|
||||
|
||||
@media (min-width: $md) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
.col-xs-2 {
|
||||
vertical-align: middle !important;
|
||||
padding: 0 !important;
|
||||
}
|
||||
|
||||
.other {
|
||||
margin-top: 30px;
|
||||
}
|
||||
|
||||
.stats {
|
||||
left: calc(16.666666666666664% + 15px);
|
||||
font-family: Consolas, "Liberation Mono", Menlo, Monaco, Courier, monospace;
|
||||
font-size: .75rem;
|
||||
|
||||
i {
|
||||
margin-left: 3px;
|
||||
font-size: .9rem;
|
||||
}
|
||||
|
||||
span {
|
||||
&:first-child {
|
||||
margin-right: 0px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
p {
|
||||
font-size: .9rem;
|
||||
color: $color-text;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.package-badge {
|
||||
position: absolute;
|
||||
right: 15px;
|
||||
bottom: -3px;
|
||||
|
||||
|
||||
@media (min-width: $md) {
|
||||
position: absolute;
|
||||
right: 0;
|
||||
bottom: 25px;
|
||||
}
|
||||
}
|
||||
|
||||
.karma , .downloads {
|
||||
color: #000;
|
||||
|
||||
span {
|
||||
transform: translate(0, 2px);
|
||||
display: inline-block;
|
||||
}
|
||||
}
|
||||
|
||||
&.liked {
|
||||
.karma {
|
||||
i {
|
||||
color: $color-red;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.name {
|
||||
font-size: 1rem;
|
||||
line-height: 1.3;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.description {
|
||||
font-size: .8rem;
|
||||
margin-top: 3px;
|
||||
max-height: 28px;
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,94 @@
|
||||
#github-contributors {
|
||||
&:not(.all) {
|
||||
.contributor {
|
||||
&:nth-child(n+17) {
|
||||
display: none;
|
||||
}
|
||||
|
||||
@media (max-width: $md) {
|
||||
&:nth-child(n+13) {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: $xs) {
|
||||
&:nth-child(n+10) {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.all {
|
||||
.button {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.loadmore {
|
||||
margin: 20px auto;
|
||||
width: 100%;
|
||||
text-align: center;
|
||||
}
|
||||
}
|
||||
|
||||
.github-contributors small.link-list {
|
||||
font-style: italic;
|
||||
font-weight: normal;
|
||||
text-transform: none;
|
||||
}
|
||||
|
||||
.contributor {
|
||||
margin-bottom: 15px;
|
||||
|
||||
.avatar {
|
||||
position: relative;
|
||||
flex: 0 0 23%;
|
||||
margin-right: 20px;
|
||||
|
||||
@media (min-width: $md) {
|
||||
flex: 0 0 15%;
|
||||
}
|
||||
|
||||
img {
|
||||
border: 3px solid #98d768;
|
||||
width: 100%;
|
||||
max-width: 112px;
|
||||
height: auto;
|
||||
}
|
||||
}
|
||||
|
||||
.counts {
|
||||
position: absolute;
|
||||
top: 2px;
|
||||
left: 2px;
|
||||
right: 2px;
|
||||
text-align: center;
|
||||
color: #fff;
|
||||
font-size: 12px;
|
||||
line-height: 12px;
|
||||
background: rgba(0,0,0,0.25);
|
||||
border-radius: 50%;
|
||||
bottom: 6px;
|
||||
padding-top: 23px;
|
||||
opacity: 0;
|
||||
transition: opacity 0.25s;
|
||||
}
|
||||
|
||||
&:hover .counts {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.contrib-count {
|
||||
position: absolute;
|
||||
left: 25px;
|
||||
bottom: 0px;
|
||||
text-align: center;
|
||||
right: 25px;
|
||||
color: #425a2e;
|
||||
font-weight: bold;
|
||||
background: darken($color-our, 4%);
|
||||
border-radius: 15px;
|
||||
z-index: 5;
|
||||
}
|
||||
}
|
||||
@@ -157,6 +157,10 @@ section.forum {
|
||||
max-width: 112px;
|
||||
height: auto;
|
||||
|
||||
.package-forum-activity & {
|
||||
border-radius: 0;
|
||||
}
|
||||
|
||||
@media (min-width: $md) {
|
||||
width: 58px;
|
||||
}
|
||||
|
||||
@@ -60,7 +60,7 @@
|
||||
@import 'sections/forum';
|
||||
@import 'sections/people';
|
||||
@import 'sections/events';
|
||||
|
||||
@import 'sections/contributors';
|
||||
|
||||
/**
|
||||
/* Pages
|
||||
|
||||
@@ -224,6 +224,18 @@
|
||||
<HintPath>..\packages\semver.1.1.2\lib\net451\Semver.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="Skybrud.Essentials, Version=1.0.8.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\Skybrud.Essentials.1.0.8\lib\net45\Skybrud.Essentials.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="Skybrud.Social.Core, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\Skybrud.Social.Core.1.0.0-beta9\lib\net45\Skybrud.Social.Core.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="Skybrud.Social.Meetup, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\Skybrud.Social.Meetup.1.0.0-beta002\lib\net45\Skybrud.Social.Meetup.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="SQLCE4Umbraco, Version=1.0.6274.27357, Culture=neutral, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\UmbracoCms.Core.7.5.11\lib\SQLCE4Umbraco.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
@@ -464,6 +476,7 @@
|
||||
<SubType>Designer</SubType>
|
||||
</Content>
|
||||
<Content Include="config\formHandlers.config" />
|
||||
<Content Include="config\githubhq.txt" />
|
||||
<Content Include="config\githubpull.config" />
|
||||
<Content Include="config\grid.editors.config.js" />
|
||||
<Content Include="config\Lang\cs-CZ.user.xml" />
|
||||
@@ -485,6 +498,7 @@
|
||||
<Content Include="config\Lang\sv-SE.user.xml" />
|
||||
<Content Include="config\Lang\zh-CN.user.xml" />
|
||||
<Content Include="config\log4net.config" />
|
||||
<Content Include="config\MeetupUmbracoGroups.txt" />
|
||||
<Content Include="config\Notification.config" />
|
||||
<Content Include="config\restExtensions.config" />
|
||||
<Content Include="config\Skinning.config" />
|
||||
@@ -4330,6 +4344,9 @@
|
||||
<Content Include="Views\Partials\Grid\Bootstrap3-Fluid.cshtml" />
|
||||
<Content Include="Views\Partials\Grid\Bootstrap2.cshtml" />
|
||||
<Content Include="Views\Partials\Grid\Bootstrap2-Fluid.cshtml" />
|
||||
<Content Include="Views\Lesson.cshtml" />
|
||||
<Content Include="Views\Partials\Home\GitHubContributors.cshtml" />
|
||||
<Content Include="Views\Partials\Home\Meetups.cshtml" />
|
||||
<None Include="web.Debug.config">
|
||||
<DependentUpon>web.config</DependentUpon>
|
||||
</None>
|
||||
@@ -4359,6 +4376,7 @@
|
||||
<VSToolsPath Condition="exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v11.0\WebApplications\Microsoft.WebApplication.targets')">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v11.0</VSToolsPath>
|
||||
<VSToolsPath Condition="exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v12.0\WebApplications\Microsoft.WebApplication.targets')">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v12.0</VSToolsPath>
|
||||
<VSToolsPath Condition="exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v14.0\WebApplications\Microsoft.WebApplication.targets')">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v14.0</VSToolsPath>
|
||||
<VSToolsPath Condition="exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v15.0\WebApplications\Microsoft.WebApplication.targets')">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v15.0</VSToolsPath>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<RunPostBuildEvent>OnBuildSuccess</RunPostBuildEvent>
|
||||
|
||||
@@ -0,0 +1,54 @@
|
||||
@using OurUmbraco.Documentation.Busineslogic
|
||||
@inherits Umbraco.Web.Mvc.UmbracoTemplatePage
|
||||
@{
|
||||
Layout = null;
|
||||
|
||||
var path = HttpContext.Current.Items[MarkdownLogic.MarkdownPathKey].ToString();
|
||||
var ml = new MarkdownLogic(path) { PrefixLinks = false, AppendAltLessonLink = true };
|
||||
|
||||
var markdown = ml.DoTransformation();
|
||||
}
|
||||
|
||||
<html>
|
||||
<head>
|
||||
<title></title>
|
||||
<link href="https://fonts.googleapis.com/css?family=Asap:400,700,400italic,700italic" type="text/css" rel="stylesheet"/>
|
||||
|
||||
<style>
|
||||
body {
|
||||
font-family: Asap, sans-serif;
|
||||
}
|
||||
|
||||
code {
|
||||
background-color: #eeeeee ;
|
||||
padding: 5px;
|
||||
}
|
||||
|
||||
pre {
|
||||
word-wrap: break-word;
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
pre > code {
|
||||
display: block;
|
||||
}
|
||||
|
||||
img {
|
||||
max-width: 90%;
|
||||
}
|
||||
|
||||
blockquote {
|
||||
border-left: 4px solid #ddd;
|
||||
padding: 1px 15px;
|
||||
color: #777;
|
||||
background: #efefef ;
|
||||
margin: 0;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div>
|
||||
@Html.Raw(markdown)
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
@@ -14,7 +14,7 @@
|
||||
|
||||
Html.RequiresCss("~/assets/css/style.min.css", 0);
|
||||
Html.RequiresCss("https://fonts.googleapis.com/css?family=Asap:400,700,400italic,700italic", 0);
|
||||
Html.RequiresCss("https://cdnjs.cloudflare.com/ajax/libs/fancybox/2.1.5/jquery.fancybox.min.css", 0);
|
||||
Html.RequiresCss("https://cdnjs.cloudflare.com/ajax/libs/fancybox/3.1.20/jquery.fancybox.min.css", 0);
|
||||
|
||||
|
||||
Html.RequiresJs("https://cdnjs.cloudflare.com/ajax/libs/jquery-validate/1.13.1/jquery.validate.min.js");
|
||||
@@ -23,7 +23,7 @@
|
||||
Html.RequiresJs("https://cdnjs.cloudflare.com/ajax/libs/pagedown/1.0/Markdown.Editor.js");
|
||||
Html.RequiresJs("https://cdnjs.cloudflare.com/ajax/libs/pagedown/1.0/Markdown.Sanitizer.js");
|
||||
Html.RequiresJs("https://cdnjs.cloudflare.com/ajax/libs/mustache.js/0.8.1/mustache.min.js");
|
||||
Html.RequiresJs("https://cdnjs.cloudflare.com/ajax/libs/fancybox/2.1.5/jquery.fancybox.min.js");
|
||||
Html.RequiresJs("https://cdnjs.cloudflare.com/ajax/libs/fancybox/3.1.20/jquery.fancybox.min.js");
|
||||
|
||||
Html.RequiresJs("~/assets/js/jquery.ajaxfileupload.js");
|
||||
|
||||
@@ -90,7 +90,7 @@
|
||||
<!--[if lt IE 9]>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/modernizr/2.7.1/modernizr.min.js"></script>
|
||||
<![endif]-->
|
||||
<script type="text/javascript" src="https://code.jquery.com/jquery-1.7.2.min.js"></script>
|
||||
<script type="text/javascript" src="https://code.jquery.com/jquery-1.9.1.min.js"></script>
|
||||
|
||||
@Html.Partial("~/Views/Partials/Community/JsValues.cshtml")
|
||||
|
||||
@@ -108,148 +108,6 @@
|
||||
ga('create', 'UA-120590-4', 'auto');
|
||||
ga('send', 'pageview');
|
||||
</script>
|
||||
<!-- temp css for survery (will be removed during May 2017) -->
|
||||
<style>
|
||||
body {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.unicorn-going-rouge {
|
||||
width: 300px;
|
||||
position: fixed;
|
||||
right: 0px;
|
||||
bottom: 0px;
|
||||
z-index: 100;
|
||||
-webkit-animation-name: fadeIn;
|
||||
animation-name: fadeIn;
|
||||
-webkit-animation-duration: 1s;
|
||||
animation-duration: 1s;
|
||||
-webkit-animation-delay: 1s;
|
||||
animation-delay: 1s;
|
||||
-webkit-animation-fill-mode: both;
|
||||
animation-fill-mode: both;
|
||||
}
|
||||
|
||||
.rouge-unicorn {
|
||||
margin: 0 auto;
|
||||
display: -webkit-box;
|
||||
display: -webkit-flex;
|
||||
display: -ms-flexbox;
|
||||
display: flex;
|
||||
-webkit-box-pack: end;
|
||||
-webkit-justify-content: flex-end;
|
||||
-ms-flex-pack: end;
|
||||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
.rouge-unicorn-famous-words {
|
||||
background: white;
|
||||
padding: 20px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.rouge-unicorn-famous-words h2 {
|
||||
font-size: 20px;
|
||||
margin-bottom: 10px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.rouge-unicorn-famous-words p {
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.rouge-unicorn-famous-words a {
|
||||
color: #4ea7ff;
|
||||
}
|
||||
|
||||
.speech-bubble {
|
||||
min-width: 300px;
|
||||
padding: 25px;
|
||||
border: 2px solid whitesmoke;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
-webkit-box-shadow: 4px 4px 10px 7px rgba(219,219,219,0.28);
|
||||
-moz-box-shadow: 4px 4px 10px 7px rgba(219,219,219,0.28);
|
||||
box-shadow: 4px 4px 10px 7px rgba(219,219,219,0.28)
|
||||
-webkit-transform: translate(-100px, -75%);
|
||||
transform: translate(-100px, -75%);
|
||||
}
|
||||
|
||||
.speech-bubble:before, .speech-bubble:after {
|
||||
content: '';
|
||||
height: 12px;
|
||||
position: absolute;
|
||||
top: 100%;
|
||||
}
|
||||
|
||||
.speech-bubble:before {
|
||||
width: 3px;
|
||||
background-color: whitesmoke;
|
||||
right: 10px;
|
||||
border-bottom-left-radius: 50px;
|
||||
border-bottom-right-radius: 100px;
|
||||
-webkit-transform: rotateY(-160deg);
|
||||
transform: rotateY(-160deg);
|
||||
}
|
||||
|
||||
.speech-bubble:after {
|
||||
width: 4px;
|
||||
background-color: whitesmoke;
|
||||
right: 16px;
|
||||
border-bottom-left-radius: 100px;
|
||||
border-bottom-right-radius: 50px;
|
||||
-webkit-transform: skew(45deg, 0);
|
||||
transform: skew(45deg, 0);
|
||||
}
|
||||
|
||||
.speech-bubble > :first-child:after, .speech-bubble > :first-child:before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
background-color: white;
|
||||
top: 100%;
|
||||
}
|
||||
|
||||
.speech-bubble > :first-child:before {
|
||||
width: 6px;
|
||||
height: 3px;
|
||||
right: 13px;
|
||||
}
|
||||
|
||||
.speech-bubble > :first-child:after {
|
||||
width: 5px;
|
||||
height: 5px;
|
||||
right: 16px;
|
||||
-webkit-transform: skew(45deg, 0);
|
||||
transform: skew(45deg, 0);
|
||||
}
|
||||
|
||||
@@-webkit-keyframes fadeIn {
|
||||
from {
|
||||
-webkit-transform: translate3d(0, 200%, 0);
|
||||
transform: translate3d(0, 200%, 0);
|
||||
}
|
||||
|
||||
to {
|
||||
-webkit-transform: translate3d(0, 0, 0);
|
||||
transform: translate3d(0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@keyframes fadeIn {
|
||||
from {
|
||||
-webkit-transform: translate3d(0, 200%, 0);
|
||||
transform: translate3d(0, 200%, 0);
|
||||
}
|
||||
|
||||
to {
|
||||
-webkit-transform: translate3d(0, 0, 0);
|
||||
transform: translate3d(0, 0, 0);
|
||||
}
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
|
||||
<body class="@bodyCss">
|
||||
@@ -317,18 +175,6 @@ box-shadow: 4px 4px 10px 7px rgba(219,219,219,0.28)
|
||||
</div>
|
||||
<!--.wrapper-->
|
||||
|
||||
<!-- temp survey markup - will be removed April 22nd 2016 -->
|
||||
<div id="unicornSurvery" class="unicorn-going-rouge" style="display: none;">
|
||||
<div class="rouge-unicorn">
|
||||
<img src="/assets/images/crap-anim.gif" alt="" />
|
||||
</div>
|
||||
|
||||
<div class="rouge-unicorn-famous-words speech-bubble">
|
||||
<h2>Let's make Umbraco better!</h2>
|
||||
<p>Ilham from the HQ is writing her Master’s thesis on Open Source Software and the dynamics within Our. It'll help us all, so please spend a max of ten minutes on this <a href="javascript:unicornClick();">survey</a> and I'll promise I'll disappear too.</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@Html.RenderJsHere()
|
||||
|
||||
<script type="text/javascript">
|
||||
@@ -336,27 +182,5 @@ box-shadow: 4px 4px 10px 7px rgba(219,219,219,0.28)
|
||||
</script>
|
||||
|
||||
@RenderSection("EndScripts", false)
|
||||
<!-- temp survey script - will be removed during May 2017 -->
|
||||
<script type="text/javascript">
|
||||
function unicornClick() {
|
||||
// set cookie
|
||||
document.cookie = 'contribSurveyTaken=true; expires=Wed, 1 Jan 2020 20:47:11 UTC; path=/';
|
||||
document.getElementById("unicornSurvery").style.display = 'none';
|
||||
var win = window.open('https://www.survey-xact.dk/LinkCollector?key=KRDR4J3C9136', '_blank');
|
||||
win.focus();
|
||||
}
|
||||
|
||||
// test for cookie
|
||||
$(document).ready(function () {
|
||||
if (document.cookie.indexOf("contribSurveyTaken") == -1) {
|
||||
// don't show on mobile devices
|
||||
var ua = navigator.userAgent;
|
||||
if (!/Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini|Mobile|mobile|CriOS/i.test(ua)) {
|
||||
|
||||
document.getElementById("unicornSurvery").style.display = 'block';
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
@using OurUmbraco.Our.Models
|
||||
@inherits OurUmbracoTemplatePage
|
||||
@using Skybrud.Social.Meetup.Models.Events
|
||||
@inherits OurUmbracoTemplatePage
|
||||
@{
|
||||
var homeNotificationText = Model.Content.GetPropertyValue<string>("homeOnlyBanner");
|
||||
var showHomeNotification = string.IsNullOrWhiteSpace(homeNotificationText) == false;
|
||||
@@ -39,7 +40,7 @@
|
||||
<!-- Search end -->
|
||||
|
||||
<style>
|
||||
.bannertext p{
|
||||
.bannertext p {
|
||||
line-height: 1.4rem;
|
||||
}
|
||||
</style>
|
||||
@@ -59,6 +60,8 @@
|
||||
@if (Members.IsLoggedIn())
|
||||
{
|
||||
@ForumActivity()
|
||||
@Meetups()
|
||||
@GitHubContributors()
|
||||
@TwitterSearch()
|
||||
@Html.Partial("home/documentation")
|
||||
}
|
||||
@@ -66,6 +69,8 @@ else
|
||||
{
|
||||
@Html.Partial("home/documentation")
|
||||
@ForumActivity()
|
||||
@Meetups()
|
||||
@GitHubContributors()
|
||||
@TwitterSearch()
|
||||
}
|
||||
|
||||
@@ -125,4 +130,61 @@ else
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
}
|
||||
|
||||
@helper GitHubContributors()
|
||||
{
|
||||
<section class="github-contributors forum">
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-12">
|
||||
<h1 class="text-center">GitHub Contributions</h1>
|
||||
<p>
|
||||
<small class="link-list">
|
||||
Contributions to default branches for
|
||||
<a href="https://github.com/umbraco/Umbraco-CMS" target="_blank" title="Umbraco-CMS">Umbraco-CMS</a>,
|
||||
<a href="https://github.com/umbraco/UmbracoDocs" target="_blank" title="UmbracoDocs">UmbracoDocs</a>,
|
||||
<a href="https://github.com/umbraco/OurUmbraco" target="_blank" title="OurUmbraco">OurUmbraco</a>,
|
||||
<a href="https://github.com/umbraco/Umbraco.Deploy.Contrib" target="_blank" title="Umbraco.Deploy.Contrib">Umbraco.Deploy.Contrib</a>,
|
||||
<a href="https://github.com/umbraco/Umbraco.Courier.Contrib" target="_blank" title="Umbraco.Courier.Contrib">Umbraco.Courier.Contrib</a> and
|
||||
<a href="https://github.com/umbraco/Umbraco.Deploy.ValueConnectors" target="_blank" title="Umbraco.Deploy.ValueConnectors">Umbraco.Deploy.ValueConnectors</a> repos
|
||||
</small>
|
||||
</p>
|
||||
</div>
|
||||
<div class="col-md-12">
|
||||
<small>Contributions the last 12 months (number indicating accepted commits)</small>
|
||||
</div>
|
||||
|
||||
<div class="col-md-12 flex forum-thread" id="github-contributors">
|
||||
<h2>Loading GitHub contributors...</h2>
|
||||
</div>
|
||||
|
||||
<div class="col-md-12 goto-forum">
|
||||
<a class="button green" href="https://our.umbraco.org/contribute">Contribute to Umbraco →</a>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
}
|
||||
|
||||
@helper Meetups() {
|
||||
<section class="forum">
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-12">
|
||||
<h1 class="text-center">Meetups</h1>
|
||||
<p>
|
||||
Upcoming meetups organized by the Umbraco community.
|
||||
</p>
|
||||
</div>
|
||||
<div class="col-md-12">
|
||||
<small>Upcoming meetups</small>
|
||||
</div>
|
||||
<div class="col-md-12 flex" id="meetups">
|
||||
<h2>Loading meetups...</h2>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
}
|
||||
@@ -1,17 +1,37 @@
|
||||
<script type="text/javascript">
|
||||
$(document).ready(function () {
|
||||
|
||||
function loadAllGitHubContributors() {
|
||||
$('#github-contributors').addClass('all');
|
||||
|
||||
}
|
||||
|
||||
$(document).ready(function() {
|
||||
try {
|
||||
$("#twitter-search").load("@Url.Action("TwitterSearchResult", "TwitterSearch", new { numberOfResults = 6 })");
|
||||
}
|
||||
catch (errTwitter) {
|
||||
$("#twitter-search").load("@Url.Action("TwitterSearchResult", "TwitterSearch", new {numberOfResults = 6})");
|
||||
} catch (errTwitter) {
|
||||
console.log("Couldn't load Twitter feed", errTwitter.message);
|
||||
}
|
||||
|
||||
try {
|
||||
$("#forum-activity").load("@Url.Action("LatestActivity", "LatestActivity", new { numberOfTopics = 6 })");
|
||||
console.log("@Url.Action("GetEvents", "Meetups")");
|
||||
$("#meetups").load("@Url.Action("GetEvents", "Meetups")");
|
||||
console.log('yay');
|
||||
}
|
||||
catch (errTwitter) {
|
||||
console.log("Couldn't load meetups", errTwitter.message);
|
||||
}
|
||||
|
||||
try {
|
||||
$("#forum-activity").load("@Url.Action("LatestActivity", "LatestActivity", new {numberOfTopics = 6})");
|
||||
} catch (errForum) {
|
||||
console.log("Couldn't load latest forum activity", errForum.message);
|
||||
}
|
||||
|
||||
try {
|
||||
$("#github-contributors").load("@Url.Action("GitHubGetContributorsResult", "GitHubContributor")");
|
||||
}
|
||||
catch (errForum) {
|
||||
console.log("Couldn't load latest forum activity", errForum.message);
|
||||
console.log("Couldn't load latest GitHub contributor activity", errForum.message);
|
||||
}
|
||||
});
|
||||
</script>
|
||||
@@ -5,6 +5,9 @@
|
||||
@inherits OurUmbraco.Our.Models.OurUmbracoTemplatePage
|
||||
|
||||
@{
|
||||
// Save query string for use in pagination links
|
||||
var queryString = HttpUtility.ParseQueryString(Request.QueryString.ToString());
|
||||
|
||||
const int pagesToShowLeft = 4;
|
||||
int page;
|
||||
if (!int.TryParse(Request["page"], out page))
|
||||
@@ -40,9 +43,9 @@
|
||||
TimeSpan.FromSeconds(4));
|
||||
}
|
||||
|
||||
var totalCountKey = "OurForumForumThreadCount[" + cat + "]";
|
||||
var totalCountKey = "OurForumForumThreadCount[" + cat + unsolved + noreplies + "]";
|
||||
var totalTopics = (int)cache.GetCacheItem(totalCountKey,
|
||||
() => topicService.GetAllTopicsCount(cat),
|
||||
() => topicService.GetAllTopicsCount(cat, unsolved, noreplies),
|
||||
TimeSpan.FromMinutes(1));
|
||||
|
||||
var pages = (totalTopics / pageSize) + 1;
|
||||
@@ -168,19 +171,22 @@
|
||||
<nav class="pagination" role="navigation">
|
||||
@if (page > 1)
|
||||
{
|
||||
<a class="prev" href="?page=@(page - 1)">Prev</a>
|
||||
queryString["page"] = (page - 1).ToString();
|
||||
<a class="prev" href="?@queryString">Prev</a>
|
||||
<span>…</span>
|
||||
}
|
||||
|
||||
@for (var i = (page - 1 > 0 ? page - 1 : 1); i < (page + (pagesToShowLeft - (page - 1 > 0 ? 1 : 0))) && i <= pages; i++)
|
||||
{
|
||||
<a class="@Umbraco.If(i == page, "active")" href="?page=@i">@i</a>
|
||||
queryString["page"] = i.ToString();
|
||||
<a class="@Umbraco.If(i == page, "active")" href="?@queryString">@i</a>
|
||||
}
|
||||
|
||||
@if (page < (pages - 3))
|
||||
@if (page < pages)
|
||||
{
|
||||
queryString["page"] = (page + 1).ToString();
|
||||
<span>…</span>
|
||||
<a class="next" href="?page=@(page + 1)">Next</a>
|
||||
<a class="next" href="?@queryString">Next</a>
|
||||
}
|
||||
</nav>
|
||||
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
@model OurUmbraco.Community.Models.GitHubContributorsModel
|
||||
|
||||
@if (Model.Contributors.Any())
|
||||
{
|
||||
foreach (var contributor in Model.Contributors)
|
||||
{
|
||||
<a href="@contributor.AuthorUrl" class="contributor" target="_blank" title="@contributor.AuthorLogin">
|
||||
<div class="avatar">
|
||||
<img alt="@contributor.AuthorLogin" src="@contributor.AuthorAvatarUrl&s=112"
|
||||
srcset="@contributor.AuthorAvatarUrl&s=224 2x, @contributor.AuthorAvatarUrl&s=336 3x" />
|
||||
<span class="contrib-count" title="@(contributor.TotalCommits + " " + (contributor.TotalCommits == 1 ? "contribution" : "contributions"))">
|
||||
@contributor.TotalCommits
|
||||
</span>
|
||||
<div class="counts">
|
||||
Additions<br />
|
||||
<strong>@contributor.TotalAdditions</strong><br />
|
||||
<br />
|
||||
Deletions<br />
|
||||
<strong>@contributor.TotalDeletions</strong>
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
}
|
||||
<div class="loadmore">
|
||||
<a class="button transparent" href="#" onclick="loadAllGitHubContributors(); return false;">Load more</a>
|
||||
</div>
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
<h2>Could not load recent GitHub contributors.</h2>
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
@using OurUmbraco.Community.Models
|
||||
@using Skybrud.Essentials.Locations
|
||||
@using Skybrud.Essentials.Locations.Extensions
|
||||
@using Skybrud.Essentials.Security
|
||||
|
||||
@inherits UmbracoViewPage<MeetupEventsModel>
|
||||
|
||||
@{
|
||||
|
||||
// Get a reference to the current member
|
||||
IPublishedContent member = Members.GetCurrentMember();
|
||||
|
||||
// Get the location of the current member (if logged in and a location is present)
|
||||
EssentialsLocation memberLocation = null;
|
||||
if (member != null && member.HasValue("latitude") && member.HasValue("longitude")) {
|
||||
memberLocation = new EssentialsLocation(
|
||||
member.GetPropertyValue<double>("latitude"),
|
||||
member.GetPropertyValue<double>("longitude")
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@foreach (MeetupItem item in Model.Items) {
|
||||
|
||||
double distance = -1;
|
||||
|
||||
if (memberLocation != null) {
|
||||
if (item.Event.HasVenue) {
|
||||
distance = memberLocation.GetDistance(item.Event.Venue);
|
||||
} else {
|
||||
distance = memberLocation.GetDistance(item.Group);
|
||||
}
|
||||
}
|
||||
|
||||
<a href="@item.Event.Link" class="forum-thread">
|
||||
@if (item.Group.GroupPhoto != null)
|
||||
{
|
||||
<div class="avatar">
|
||||
<img src="@item.Group.GroupPhoto.ThumbLink" alt="" />
|
||||
</div>
|
||||
}
|
||||
else
|
||||
{
|
||||
string fakeHash = SecurityUtils.GetMd5Hash(item.Group.Id + "");
|
||||
<div class="avatar">
|
||||
<img src="https://www.gravatar.com/avatar/@fakeHash?s=100&d=mm&r=g&d=retro" alt="" />
|
||||
</div>
|
||||
|
||||
}
|
||||
<div class="meta">
|
||||
<div class="forum-thread-text">
|
||||
@if (distance >= 0 && distance <= 50000) {
|
||||
//<span style="float: right; color: red;">@String.Format("~{0:N0}", distance / 1000) km</span>
|
||||
<span style="float: right; color: red; font-weight: bold;" title="Distance: @String.Format("~{0:N0}", distance / 1000) km">NEAR YOU</span>
|
||||
}
|
||||
<h3>@item.Event.Name</h3>
|
||||
<p>@item.Event.Time.DateTime.ToString("MMM d, yyyy") by @item.Group.Name</p>
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
}
|
||||
|
||||
@if (Model.Items.Length % 2 == 1) {
|
||||
// If there is an odd amount of events, we add a invisible div so the last event doesn't take up the full width
|
||||
<div class="forum-thread" style="visibility: hidden;"></div>
|
||||
}
|
||||
|
||||
@if (Model.Items.Any() == false) {
|
||||
<h2>Could not load upcoming meetups.</h2>
|
||||
}
|
||||
@@ -185,7 +185,9 @@
|
||||
defaultScreenshot = childContent.GetPropertyValue("defaultScreenshotPath", false, "/css/img/package2.png");
|
||||
}
|
||||
}
|
||||
<img src="@Utils.GetScreenshotPath(defaultScreenshot)?bgcolor=fff&width=50&height=50&format=png" />
|
||||
<img src="@Utils.GetScreenshotPath(defaultScreenshot)?bgcolor=fff&width=50&height=50&format=png"
|
||||
srcset="@Utils.GetScreenshotPath(defaultScreenshot)?bgcolor=fff&width=100&height=100&format=png 2x,
|
||||
@Utils.GetScreenshotPath(defaultScreenshot)?bgcolor=fff&width=150&height=150&format=png 3x" />
|
||||
</div>
|
||||
<div class="col-xs-10 col-md-6">
|
||||
<div class="forum-thread-text">
|
||||
|
||||
@@ -81,7 +81,7 @@
|
||||
|
||||
@foreach (var image in screenshots)
|
||||
{
|
||||
<a class="fancybox" rel="gallery1" href="@Utils.GetScreenshotPath(image.Path)" title="">
|
||||
<a class="fancybox" data-fancybox="package-gallery" href="@Utils.GetScreenshotPath(image.Path)" title="">
|
||||
<img src="@Utils.GetScreenshotPath(image.Path)?bgcolor=fff&height=154&width=281&format=png" alt=""/>
|
||||
</a>
|
||||
}
|
||||
@@ -236,7 +236,7 @@
|
||||
<a href="@forum.Url" class="forum-thread">
|
||||
<div class="row">
|
||||
|
||||
<div class="col-xs-10 col-md-0">
|
||||
<div class="col-xs-12 col-md-12">
|
||||
<div class="forum-thread-text">
|
||||
<h3>@forum.Name</h3>
|
||||
<p>@forum.forumDescription</p>
|
||||
|
||||
@@ -18,9 +18,10 @@
|
||||
(function () {
|
||||
$(".fancybox")
|
||||
.fancybox({
|
||||
openEffect: 'none',
|
||||
closeEffect: 'none',
|
||||
padding: 0
|
||||
// options
|
||||
loop: true,
|
||||
arrows: true,
|
||||
infobar: false
|
||||
});
|
||||
})();
|
||||
</script>
|
||||
|
||||
@@ -10,7 +10,7 @@ NOTES:
|
||||
* Compression/Combination/Minification is not enabled unless debug="false" is specified on the 'compiliation' element in the web.config
|
||||
* A new version will invalidate both client and server cache and create new persisted files
|
||||
-->
|
||||
<clientDependency version="463511010" fileDependencyExtensions=".js,.css" loggerType="Umbraco.Web.UI.CdfLogger, umbraco">
|
||||
<clientDependency version="49321111" fileDependencyExtensions=".js,.css" loggerType="Umbraco.Web.UI.CdfLogger, umbraco">
|
||||
|
||||
<!--
|
||||
This section is used for Web Forms only, the enableCompositeFiles="true" is optional and by default is set to true.
|
||||
|
||||
@@ -0,0 +1,36 @@
|
||||
umbracodk
|
||||
Dutch-Umbraco-User-Group
|
||||
Australian-Umbraco-Meetups
|
||||
Kent-Umbraco-Meetup
|
||||
Sydney-Umbraco-Meetup
|
||||
Umbraco-Meetup-RheinMain
|
||||
The-London-Umbraco-Meetup
|
||||
Denver-Area-Umbraco-Meetup
|
||||
Auckland-Umbraco-Meetup
|
||||
Denver-Area-Umbraco-Meetup
|
||||
Dorset-Umbraco-Meetup
|
||||
Umbraco-Oxford-Meetup
|
||||
Madrid-Umbraco-Meetup-Group
|
||||
Chicago-Umbraco-Meetup
|
||||
Umbraco
|
||||
Umbraco-Dev-TC
|
||||
Goteborg-Umbraco-Meetup
|
||||
Dublin-Umbraco-Meetup
|
||||
Umbraco-BA
|
||||
Manchester-Umbraco-Meetup
|
||||
Liverpool-Umbraco-Meetup
|
||||
The-Poland-Umbraco-Meetup
|
||||
Lisbon-Umbraco-Meetup
|
||||
Glasgow-Umbraco-Users-Group-GLUUG
|
||||
PNW-Umbraco-Meetup
|
||||
Adelaide-Umbraco-Meetup
|
||||
The-New-York-Umbraco-Meetup
|
||||
Umbraco-Navi-Mumbai-NET-Meetup
|
||||
Edinburgh-Umbraco-Users-Group
|
||||
Stuttgart-Umbraco-Meetup
|
||||
UmbCardiff
|
||||
meet-umbraco-the-umbraco-meetup
|
||||
umBristol
|
||||
Oslo-Umbraco-Meetup
|
||||
Orange-County-Umbraco-Web-Technologies
|
||||
umbLeeds
|
||||
@@ -0,0 +1,16 @@
|
||||
Aaen
|
||||
clausjensen
|
||||
emilwangaa
|
||||
hartvig
|
||||
hemraker
|
||||
madsrasmussen
|
||||
mikkelhm
|
||||
nul800sebastiaan
|
||||
perploug
|
||||
Shazwazza
|
||||
simonbusborg
|
||||
sitereactor
|
||||
sofietoft
|
||||
umbracoci
|
||||
warrenbuckley
|
||||
zpqrtbnk
|
||||
@@ -2,5 +2,7 @@
|
||||
<configuration>
|
||||
<sources>
|
||||
<add url="https://github.com/umbraco/UmbracoDocs/archive/master.zip" folder="" />
|
||||
<!-- Comma separated list of branches we will pull documentation from -->
|
||||
<allowedBranches>master</allowedBranches>
|
||||
</sources>
|
||||
</configuration>
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
var packageRepoService = new PackageRepositoryService(umbracoHelper, umbracoHelper.MembershipHelper, ApplicationContext.Current.DatabaseContext);
|
||||
//This doesn't matter what we set it to so long as it's below 7.5 since that is the version we introduce strict dependencies
|
||||
var currUmbracoVersion = new Version(4, 0, 0);
|
||||
var packageDetails = packageRepoService.GetDetails(Project.ProjectGuid, currUmbracoVersion);
|
||||
var packageDetails = packageRepoService.GetDetails(Project.ProjectGuid, currUmbracoVersion, false);
|
||||
|
||||
if (packageDetails == null)
|
||||
{
|
||||
|
||||
@@ -56,6 +56,9 @@
|
||||
<package id="RestSharp" version="104.1" targetFramework="net4" />
|
||||
<package id="semver" version="1.1.2" targetFramework="net452" />
|
||||
<package id="SharpZipLib" version="0.86.0" targetFramework="net452" />
|
||||
<package id="Skybrud.Essentials" version="1.0.8" targetFramework="net452" />
|
||||
<package id="Skybrud.Social.Core" version="1.0.0-beta9" targetFramework="net452" />
|
||||
<package id="Skybrud.Social.Meetup" version="1.0.0-beta002" targetFramework="net452" />
|
||||
<package id="System.Collections.Immutable" version="1.1.36" targetFramework="net452" />
|
||||
<package id="System.Reflection.Metadata" version="1.0.21" targetFramework="net452" />
|
||||
<package id="TweetinviAPI" version="1.2.0" targetFramework="net452" />
|
||||
|
||||
@@ -105,6 +105,7 @@
|
||||
<add key="SpamBlockThreshold" value="90" />
|
||||
<add key="ValidationSettings:UnobtrusiveValidationMode" value="None" />
|
||||
<add key="UmbracoStarterKits" value="55E028E3-0C5B-4188-9722-7D14B4BD12C0,69E44BEB-15FF-4CEE-8B64-0A7DAE498657,0B0101F7-9394-48F3-A581-DD3F18480265" />
|
||||
<add key="UmbracoStarterKitDefault" value="ced954d1-8c0f-4abe-bdda-99e7a787d052"/>
|
||||
|
||||
<add key="SlackChannel" value="#our-spam-reports" />
|
||||
<add key="SlackToken" value="" />
|
||||
@@ -307,7 +308,7 @@
|
||||
</buildProviders>
|
||||
</compilation>
|
||||
<authentication mode="Forms">
|
||||
<forms name="yourAuthCookie" loginUrl="login.aspx" protection="All" path="/" slidingExpiration="true" timeout="525600" />
|
||||
<forms requireSSL="true" name="yourAuthCookie" loginUrl="login.aspx" protection="All" path="/" slidingExpiration="true" timeout="525600" />
|
||||
</authentication>
|
||||
<authorization>
|
||||
<allow users="?" />
|
||||
@@ -505,6 +506,10 @@
|
||||
</conditions>
|
||||
<action type="Redirect" url="{C:1}" redirectType="Permanent" appendQueryString="true" />
|
||||
</rule>
|
||||
<rule name="DocsProductsToAddons" patternSyntax="Wildcard" stopProcessing="true">
|
||||
<match url="documentation/products/*" />
|
||||
<action type="Redirect" url="/documentation/Add-ons/{R:1}" redirectType="Permanent" appendQueryString="true" />
|
||||
</rule>
|
||||
<!-- WIKI -->
|
||||
<rule name="RedirectWikiEvents" patternSyntax="Wildcard">
|
||||
<match url="wiki/reference/api-cheatsheet/using-applicationbase-to-register-events/*" />
|
||||
@@ -690,4 +695,4 @@
|
||||
</httpProtocol>
|
||||
</system.webServer>
|
||||
</location>
|
||||
</configuration>
|
||||
</configuration>
|
||||
|
||||
@@ -0,0 +1,173 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net;
|
||||
using System.Web.Mvc;
|
||||
using OurUmbraco.Community.Models;
|
||||
using OurUmbraco.Our.Api;
|
||||
using RestSharp;
|
||||
using Umbraco.Core.Cache;
|
||||
using Umbraco.Core.Logging;
|
||||
using Umbraco.Web.Mvc;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using Newtonsoft.Json;
|
||||
using System.Text;
|
||||
|
||||
namespace OurUmbraco.Community.Controllers
|
||||
{
|
||||
public class GitHubContributorController : SurfaceController
|
||||
{
|
||||
/// <summary>
|
||||
/// Repositories to include in the combination of contributions
|
||||
/// </summary>
|
||||
private readonly string[] Repositories =
|
||||
{
|
||||
"Umbraco-CMS",
|
||||
"UmbracoDocs",
|
||||
"OurUmbraco",
|
||||
"Umbraco.Deploy.Contrib",
|
||||
"Umbraco.Courier.Contrib",
|
||||
"Umbraco.Deploy.ValueConnectors"
|
||||
};
|
||||
|
||||
protected string JsonPath
|
||||
{
|
||||
get { return Server.MapPath("~/App_Data/TEMP/GithubContributors.json"); }
|
||||
}
|
||||
|
||||
public List<GitHubCachedGlobalContributorModel> GetCachedContributors()
|
||||
{
|
||||
|
||||
if (!System.IO.File.Exists(JsonPath)) throw new Exception("The JSON file doesn't exist on disk");
|
||||
|
||||
|
||||
List<GitHubCachedGlobalContributorModel> temp = new List<GitHubCachedGlobalContributorModel>();
|
||||
|
||||
// Parse the JSON file from disk
|
||||
foreach (JToken token in Skybrud.Essentials.Json.JsonUtils.LoadJsonArray(JsonPath))
|
||||
{
|
||||
|
||||
temp.Add(token.ToObject<GitHubCachedGlobalContributorModel>());
|
||||
|
||||
}
|
||||
|
||||
return temp;
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets data for all GitHub contributors for all listed Umbraco repositories,
|
||||
/// excluding the GitHub IDs of the HQ contributors from the text file list
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
public ActionResult GitHubGetContributorsResult(bool force = false)
|
||||
{
|
||||
var model = new GitHubContributorsModel();
|
||||
model.Contributors = new List<GitHubCachedGlobalContributorModel>();
|
||||
|
||||
try
|
||||
{
|
||||
|
||||
// If the file exists on disk and hasn't expired (AKA not older than one day), we should just load that
|
||||
if (force == false && System.IO.File.Exists(JsonPath) && System.IO.File.GetLastWriteTimeUtc(JsonPath) >= DateTime.UtcNow.AddDays(-1))
|
||||
{
|
||||
model.Contributors = GetCachedContributors();
|
||||
return PartialView("~/Views/Partials/Home/GitHubContributors.cshtml", model);
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
// Load the contributors via the GitHub API and map to the cached model
|
||||
var contributors = GetContributors().Select(x => new GitHubCachedGlobalContributorModel(x));
|
||||
|
||||
// Serialize the contributors to raw JSON
|
||||
string rawJson = JsonConvert.SerializeObject(contributors, Formatting.Indented);
|
||||
|
||||
// Save the JSON to disk
|
||||
System.IO.File.WriteAllText(JsonPath, rawJson, Encoding.UTF8);
|
||||
|
||||
model.Contributors = contributors.ToList();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
// Log the error so we can debug it later
|
||||
LogHelper.Error<GitHubContributorController>("Unable to load GitHub contributors from the GitHub API", ex);
|
||||
|
||||
// Load the contributors from the cache (if we have any)
|
||||
model.Contributors = GetCachedContributors();
|
||||
}
|
||||
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
// Log the error so we can debug it later
|
||||
LogHelper.Error<GitHubContributorController>("Unable to load GitHub contributors from the GitHub API", ex);
|
||||
|
||||
}
|
||||
|
||||
return PartialView("~/Views/Partials/Home/GitHubContributors.cshtml", model);
|
||||
}
|
||||
|
||||
public List<GitHubGlobalContributorModel> GetContributors()
|
||||
{
|
||||
|
||||
|
||||
string configPath = Server.MapPath("~/config/githubhq.txt");
|
||||
if (!System.IO.File.Exists(configPath))
|
||||
{
|
||||
LogHelper.Debug<GitHubContributorController>("Config file was not found: " + configPath);
|
||||
throw new Exception("Config file was not found: " + configPath);
|
||||
}
|
||||
|
||||
string[] login = System.IO.File.ReadAllLines(configPath).Where(x => x.Trim() != "").Distinct().ToArray();
|
||||
|
||||
var githubController = new GitHubController();
|
||||
var gitHubContributors = new List<GitHubContributorModel>();
|
||||
foreach (var repo in Repositories)
|
||||
{
|
||||
var response = githubController.GetAllRepoContributors(repo);
|
||||
if (response.StatusCode == HttpStatusCode.OK &&
|
||||
response.ResponseStatus == ResponseStatus.Completed)
|
||||
{
|
||||
gitHubContributors.AddRange(response.Data);
|
||||
}
|
||||
else
|
||||
{
|
||||
LogHelper.Warn<IGitHubContributorsModel>(string.Format("Invalid HTTP response for repository {0}", repo));
|
||||
}
|
||||
}
|
||||
|
||||
// filter to only include items from the last year (if we ran 4.6.1 we could have used ToUnixTimeSeconds())
|
||||
var filteredRange = DateTime.UtcNow.AddYears(-1).Subtract(new DateTime(1970, 1, 1)).TotalSeconds;
|
||||
|
||||
foreach (var contrib in gitHubContributors)
|
||||
{
|
||||
var contribWeeks = contrib.Weeks.Where(x => x.W >= filteredRange).ToList();
|
||||
contrib.TotalAdditions = contribWeeks.Sum(x => x.A);
|
||||
contrib.TotalDeletions = contribWeeks.Sum(x => x.D);
|
||||
contrib.Total = contribWeeks.Sum(x => x.C);
|
||||
}
|
||||
|
||||
var filteredContributors = gitHubContributors
|
||||
.Where(g => !login.Contains(g.Author.Login))
|
||||
.GroupBy(g => g.Author.Id)
|
||||
.OrderByDescending(c => c.Sum(g => g.Total));
|
||||
|
||||
List<GitHubGlobalContributorModel> temp = new List<GitHubGlobalContributorModel>();
|
||||
|
||||
foreach (var group in filteredContributors)
|
||||
{
|
||||
var contributor = new GitHubGlobalContributorModel(group);
|
||||
if (contributor.TotalCommits > 0)
|
||||
{
|
||||
temp.Add(contributor);
|
||||
}
|
||||
}
|
||||
|
||||
return temp;
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,75 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using OurUmbraco.Community.Models;
|
||||
|
||||
namespace OurUmbraco.Community.Controllers
|
||||
{
|
||||
|
||||
public class GitHubCachedGlobalContributorModel
|
||||
{
|
||||
|
||||
public int AuthorId { get; set; }
|
||||
|
||||
public string AuthorLogin { get; set; }
|
||||
|
||||
public string AuthorUrl { get; set; }
|
||||
|
||||
public string AuthorAvatarUrl { get; set; }
|
||||
|
||||
public int TotalCommits { get; set; }
|
||||
|
||||
public int TotalAdditions { get; set; }
|
||||
|
||||
public int TotalDeletions { get; set; }
|
||||
|
||||
public GitHubCachedGlobalContributorModel() { }
|
||||
|
||||
public GitHubCachedGlobalContributorModel(GitHubGlobalContributorModel contributor)
|
||||
{
|
||||
AuthorId = contributor.Author.Id;
|
||||
AuthorLogin = contributor.Author.Login;
|
||||
AuthorUrl = contributor.Author.HtmlUrl;
|
||||
AuthorAvatarUrl = contributor.Author.AvatarUrl;
|
||||
TotalCommits = contributor.TotalCommits;
|
||||
TotalAdditions = contributor.TotalAdditions;
|
||||
TotalDeletions = contributor.TotalDeletions;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public class GitHubGlobalContributorModel
|
||||
{
|
||||
public List<GitHubContributorModel> Items { get; set; }
|
||||
|
||||
public int Id
|
||||
{
|
||||
get { return Author.Id; }
|
||||
}
|
||||
|
||||
public int TotalCommits
|
||||
{
|
||||
get { return Items.Sum(x => x.Total); }
|
||||
}
|
||||
|
||||
public int TotalAdditions
|
||||
{
|
||||
get { return Items.Sum(x => x.TotalAdditions); }
|
||||
}
|
||||
|
||||
public int TotalDeletions
|
||||
{
|
||||
get { return Items.Sum(x => x.TotalDeletions); }
|
||||
}
|
||||
|
||||
public Author Author
|
||||
{
|
||||
get { return Items.First().Author; }
|
||||
}
|
||||
|
||||
public GitHubGlobalContributorModel(IEnumerable<GitHubContributorModel> items)
|
||||
{
|
||||
Items = items.ToList();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Web.Mvc;
|
||||
using OurUmbraco.Community.Models;
|
||||
using Skybrud.Essentials.Json.Extensions;
|
||||
using Skybrud.Social.Meetup;
|
||||
using Skybrud.Social.Meetup.Models.Events;
|
||||
using Skybrud.Social.Meetup.Models.Groups;
|
||||
using Skybrud.Social.Meetup.Responses.Events;
|
||||
using Skybrud.Social.Meetup.Responses.Groups;
|
||||
using Umbraco.Core.Logging;
|
||||
using Umbraco.Web.Mvc;
|
||||
using Umbraco.Core.Cache;
|
||||
|
||||
namespace OurUmbraco.Community.Controllers {
|
||||
|
||||
public class MeetupsController : SurfaceController {
|
||||
|
||||
public ActionResult GetEvents() {
|
||||
|
||||
MeetupEventsModel model = new MeetupEventsModel {
|
||||
Items = new MeetupItem[0]
|
||||
};
|
||||
|
||||
try {
|
||||
|
||||
string configPath = Server.MapPath("~/config/MeetupUmbracoGroups.txt");
|
||||
if (!System.IO.File.Exists(configPath)) {
|
||||
LogHelper.Debug<MeetupsController>("Config file was not found: " + configPath);
|
||||
return PartialView("~/Views/Partials/Home/Meetups.cshtml", model);
|
||||
}
|
||||
|
||||
// Get the alias (urlname) of each group from the config file
|
||||
string[] aliases = System.IO.File.ReadAllLines(configPath).Where(x => x.Trim() != "").Distinct().ToArray();
|
||||
|
||||
model.Items =
|
||||
ApplicationContext.ApplicationCache.RuntimeCache.GetCacheItem<MeetupItem[]>("UmbracoSearchedMeetups",
|
||||
() => {
|
||||
|
||||
// Initialize a new service instance (we don't specify an API key since we're accessing public data)
|
||||
MeetupService service = new MeetupService();
|
||||
|
||||
List<MeetupItem> items = new List<MeetupItem>();
|
||||
|
||||
foreach (string alias in aliases) {
|
||||
|
||||
try {
|
||||
|
||||
// Get information about the group
|
||||
MeetupGroup group = service.Groups.GetGroup(alias).Body;
|
||||
|
||||
if (group.JObject.HasValue("next_event")) {
|
||||
|
||||
string nextEventId = group.JObject.GetString("next_event.id");
|
||||
|
||||
// Make the call to the Meetup.com API to get upcoming events
|
||||
MeetupGetEventsResponse res = service.Events.GetEvents(alias);
|
||||
|
||||
// Get the next event(s)
|
||||
MeetupEvent nextEvent = res.Body.FirstOrDefault(x => x.Id == nextEventId);
|
||||
|
||||
// Append the first event of the group
|
||||
if (nextEvent != null) items.Add(new MeetupItem(group, nextEvent));
|
||||
|
||||
}
|
||||
|
||||
} catch (Exception ex) {
|
||||
LogHelper.Error<MeetupsController>("Could not get events from meetup.com for group with alias: " + alias, ex);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return items.OrderBy(x => x.Event.Time).ToArray();
|
||||
|
||||
}, TimeSpan.FromMinutes(30));
|
||||
|
||||
|
||||
} catch (Exception ex) {
|
||||
LogHelper.Error<MeetupsController>("Could not get events from meetup.com", ex);
|
||||
}
|
||||
|
||||
return PartialView("~/Views/Partials/Home/Meetups.cshtml", model);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -60,7 +60,8 @@ namespace OurUmbraco.Community.Controllers
|
||||
x.CreatedBy.UserIdentifier.ScreenName.ToLowerInvariant().ContainsAny(usernameFilter) ==
|
||||
false
|
||||
&& x.UserMentions.Any(m => m.ScreenName.ContainsAny(usernameFilter)) == false
|
||||
&& x.Text.ToLowerInvariant().ContainsAny(wordFilter) == false)
|
||||
&& x.Text.ToLowerInvariant().ContainsAny(wordFilter) == false
|
||||
&& x.Text.StartsWith("RT ") == false)
|
||||
.Take(numberOfResults)
|
||||
.ToArray();
|
||||
}
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
using System.Collections.Generic;
|
||||
using OurUmbraco.Community.Controllers;
|
||||
|
||||
namespace OurUmbraco.Community.Models
|
||||
{
|
||||
public class GitHubContributorsModel : IGitHubContributorsModel
|
||||
{
|
||||
public List<GitHubCachedGlobalContributorModel> Contributors { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,117 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace OurUmbraco.Community.Models
|
||||
{
|
||||
[DataContract]
|
||||
public class GitHubContributorModel : IGitHubContributorModel
|
||||
{
|
||||
|
||||
private List<Week> _weeks;
|
||||
|
||||
public int Total { get; set; }
|
||||
public int TotalAdditions { get; set; }
|
||||
public int TotalDeletions { get; set; }
|
||||
|
||||
[DataMember(Name = "weeks")]
|
||||
public List<Week> Weeks
|
||||
{
|
||||
get { return _weeks; }
|
||||
|
||||
set
|
||||
{
|
||||
_weeks = value;
|
||||
|
||||
|
||||
int totalAdditions = 0;
|
||||
int totalDeletions = 0;
|
||||
foreach (var week in _weeks)
|
||||
{
|
||||
totalDeletions += week.D;
|
||||
totalAdditions += week.A;
|
||||
}
|
||||
|
||||
TotalAdditions = totalAdditions;
|
||||
TotalDeletions = totalDeletions;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
public Author Author { get; set; }
|
||||
}
|
||||
|
||||
[DataContract]
|
||||
public class Week
|
||||
{
|
||||
/// <summary>
|
||||
/// Timestamp
|
||||
/// </summary>
|
||||
public int W { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Additions
|
||||
/// </summary>
|
||||
public int A { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Deletions
|
||||
/// </summary>
|
||||
public int D { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Commits
|
||||
/// </summary>
|
||||
public int C { get; set; }
|
||||
}
|
||||
|
||||
[DataContract]
|
||||
public class Author
|
||||
{
|
||||
public string Login { get; set; }
|
||||
|
||||
public int Id { get; set; }
|
||||
|
||||
[DataMember(Name = "avatar_url")]
|
||||
public string AvatarUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "gravatar_id")]
|
||||
public string GravatarId { get; set; }
|
||||
|
||||
public string Url { get; set; }
|
||||
|
||||
[DataMember(Name = "html_url")]
|
||||
public string HtmlUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "followers_url")]
|
||||
public string FollowersUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "following_url")]
|
||||
public string FollowingsUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "gists_url")]
|
||||
public string GistsUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "starred_url")]
|
||||
public string StarredUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "subscriptions_url")]
|
||||
public string SubscriptionsUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "organizations_url")]
|
||||
public string OrganizationsUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "repos_url")]
|
||||
public string ReposUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "events_url")]
|
||||
public string EventsUrl { get; set; }
|
||||
|
||||
[DataMember(Name = "received_events_url")]
|
||||
public string ReceivedEventsUrl { get; set; }
|
||||
|
||||
public string Type { get; set; }
|
||||
|
||||
[DataMember(Name = "site_admin")]
|
||||
public bool SiteAdmin { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
namespace OurUmbraco.Community.Models
|
||||
{
|
||||
public interface IGitHubContributorModel
|
||||
{
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
namespace OurUmbraco.Community.Models
|
||||
{
|
||||
public interface IGitHubContributorsModel
|
||||
{
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
namespace OurUmbraco.Community.Models {
|
||||
|
||||
public class MeetupEventsModel {
|
||||
|
||||
public MeetupItem[] Items { get; set; }
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
using Skybrud.Essentials.Locations;
|
||||
using Skybrud.Social.Meetup.Models.Events;
|
||||
using Skybrud.Social.Meetup.Models.Groups;
|
||||
|
||||
namespace OurUmbraco.Community.Models {
|
||||
|
||||
public class MeetupItem {
|
||||
|
||||
public MeetupGroup Group { get; set; }
|
||||
|
||||
public MeetupEvent Event { get; set; }
|
||||
|
||||
public ILocation Location {
|
||||
get { return Event.HasVenue ? (ILocation) Event.Venue : Group; }
|
||||
}
|
||||
|
||||
public MeetupItem(MeetupGroup group, MeetupEvent ev) {
|
||||
Group = group;
|
||||
Event = ev;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -3,13 +3,10 @@ using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Linq.Expressions;
|
||||
using System.Net;
|
||||
using System.Web;
|
||||
using System.Web.Hosting;
|
||||
using System.Xml;
|
||||
using Examine;
|
||||
using ICSharpCode.SharpZipLib.Zip;
|
||||
using Newtonsoft.Json;
|
||||
using Umbraco.Core.Logging;
|
||||
using ZipFile = System.IO.Compression.ZipFile;
|
||||
@@ -112,21 +109,46 @@ namespace OurUmbraco.Documentation.Busineslogic.GithubSourcePull
|
||||
FireOnFinish(finishEventArgs);
|
||||
}
|
||||
|
||||
public dynamic DocumentationSiteMap(string folder = "")
|
||||
public SiteMapItem DocumentationSiteMap(string folder = "")
|
||||
{
|
||||
var path = Path.Combine(RootFolder, folder, "sitemap.js");
|
||||
var json = File.ReadAllText(path);
|
||||
dynamic documentationSiteMap = JsonConvert.DeserializeObject<dynamic>(json);
|
||||
return documentationSiteMap;
|
||||
return JsonConvert.DeserializeObject<SiteMapItem>(json);
|
||||
}
|
||||
|
||||
public void Process(string url, string foldername)
|
||||
{
|
||||
var zip = Download(url, foldername);
|
||||
RemoveExistingDocumentation(RootFolder);
|
||||
var unzippedPath = string.Empty;
|
||||
var branchAllowed = false;
|
||||
|
||||
using (var zipFile = ZipFile.OpenRead(zip))
|
||||
{
|
||||
var directory = zipFile.Entries.FirstOrDefault();
|
||||
|
||||
if (directory != null)
|
||||
{
|
||||
var branch = directory.FullName.Replace("/", string.Empty).Replace("UmbracoDocs-", string.Empty);
|
||||
branchAllowed = IsBranchWhiteListed(branch);
|
||||
|
||||
if (branchAllowed)
|
||||
{
|
||||
unzippedPath = RootFolder + Path.DirectorySeparatorChar +
|
||||
directory.FullName.Replace('/', Path.DirectorySeparatorChar);
|
||||
if (Directory.Exists(unzippedPath))
|
||||
//delete the directory we're trying to unzip to
|
||||
RemoveUnzippedFiles(unzippedPath);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (branchAllowed == false)
|
||||
return;
|
||||
|
||||
ZipFile.ExtractToDirectory(zip, RootFolder);
|
||||
|
||||
var unzippedPath = RootFolder + "\\UmbracoDocs-master\\";
|
||||
RemoveUnzippedFiles(RootFolder, ignoreDirectories: new List<string> { unzippedPath });
|
||||
|
||||
foreach (var directory in new DirectoryInfo(unzippedPath).GetDirectories())
|
||||
Directory.Move(directory.FullName, RootFolder + "\\" + directory.Name);
|
||||
foreach (var file in new DirectoryInfo(unzippedPath).GetFiles())
|
||||
@@ -140,16 +162,35 @@ namespace OurUmbraco.Documentation.Busineslogic.GithubSourcePull
|
||||
ExamineManager.Instance.IndexProviderCollection["documentationIndexer"].RebuildIndex();
|
||||
}
|
||||
|
||||
private bool IsBranchWhiteListed(string branch)
|
||||
{
|
||||
var xmlNodeList = Configuration.SelectNodes("//allowedBranches");
|
||||
if (xmlNodeList == null || xmlNodeList.Count <= 0)
|
||||
return false;
|
||||
|
||||
var node = xmlNodeList[0];
|
||||
if (string.IsNullOrWhiteSpace(node.InnerText))
|
||||
return false;
|
||||
|
||||
var allowedBranches = node.InnerText.Split(',');
|
||||
var isBranchWhitelisted = allowedBranches.Any(allowedBranch => allowedBranch.Equals(branch, StringComparison.InvariantCultureIgnoreCase));
|
||||
|
||||
if (isBranchWhitelisted == false)
|
||||
LogHelper.Warn<ZipDownloader>(string.Format("The branch {0} is not allowed in githubpull.config, will not process documentation any further", branch));
|
||||
|
||||
return isBranchWhitelisted;
|
||||
}
|
||||
|
||||
public void BuildSitemap(string foldername)
|
||||
{
|
||||
var folder = new DirectoryInfo(Path.Combine(RootFolder, foldername));
|
||||
dynamic root = GetFolderStructure(folder, folder.FullName, 0);
|
||||
var root = GetFolderStructure(folder, folder.FullName, 0);
|
||||
|
||||
var serializedRoot = JsonConvert.SerializeObject(root, Newtonsoft.Json.Formatting.Indented);
|
||||
File.WriteAllText(Path.Combine(folder.FullName, "sitemap.js"), serializedRoot);
|
||||
}
|
||||
|
||||
private class SiteMapItem
|
||||
public class SiteMapItem
|
||||
{
|
||||
public string name { get; set; }
|
||||
public string path { get; set; }
|
||||
@@ -157,28 +198,37 @@ namespace OurUmbraco.Documentation.Busineslogic.GithubSourcePull
|
||||
public int sort { get; set; }
|
||||
public bool hasChildren { get; set; }
|
||||
public List<SiteMapItem> directories { get; set; }
|
||||
|
||||
//public string url => $"http://localhost:24292/documentation{this.path}/?altTemplate=Lesson";
|
||||
|
||||
public string url
|
||||
{
|
||||
get
|
||||
{
|
||||
return string.Format("https://our.umbraco.org/documentation{0}/?altTemplate=Lesson", this.path);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private SiteMapItem GetFolderStructure(DirectoryInfo dir, string rootPath, int level)
|
||||
{
|
||||
var list = new List<SiteMapItem>();
|
||||
|
||||
var siteMapItem = new SiteMapItem
|
||||
{
|
||||
name = dir.Name.Replace("-", " "),
|
||||
path = dir.FullName.Substring(rootPath.Length).Replace('\\', '/'),
|
||||
level = level,
|
||||
sort = GetSort(dir.Name, level) ?? 100
|
||||
sort = GetSort(dir.Name, level) ?? 100,
|
||||
directories = list,
|
||||
hasChildren = dir.GetDirectories().Any()
|
||||
};
|
||||
|
||||
if (dir.GetDirectories().Any() == false)
|
||||
return siteMapItem;
|
||||
|
||||
var list = new List<SiteMapItem>();
|
||||
foreach (var child in dir.GetDirectories().Where(x => x.Name != "images"))
|
||||
{
|
||||
list.Add(GetFolderStructure(child, rootPath, level + 1));
|
||||
}
|
||||
|
||||
siteMapItem.hasChildren = true;
|
||||
siteMapItem.directories = list.OrderBy(x => x.sort).ToList();
|
||||
|
||||
return siteMapItem;
|
||||
@@ -444,21 +494,35 @@ namespace OurUmbraco.Documentation.Busineslogic.GithubSourcePull
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
private static void RemoveExistingDocumentation(string folder)
|
||||
|
||||
private static void RemoveUnzippedFiles(string folder, List<string> ignoreDirectories = null)
|
||||
{
|
||||
if (Directory.Exists(folder))
|
||||
{
|
||||
foreach (var directory in Directory.GetDirectories(folder))
|
||||
Retry.Do(() => Directory.Delete(directory, true), TimeSpan.FromSeconds(1), 5);
|
||||
{
|
||||
if (ignoreDirectories == null || ignoreDirectories.Any() == false)
|
||||
{
|
||||
//there are no ignores, so proceed to delete it
|
||||
Retry.Do(() => Directory.Delete(directory, true), TimeSpan.FromSeconds(1), 5);
|
||||
}
|
||||
else
|
||||
{
|
||||
foreach (var ignoreDirectory in ignoreDirectories)
|
||||
{
|
||||
if (ignoreDirectory.TrimEnd('\\').Equals(directory.TrimEnd('\\'),
|
||||
StringComparison.InvariantCultureIgnoreCase) == false)
|
||||
{
|
||||
//path is NOT in the ignore list, so proceed to delete it
|
||||
Retry.Do(() => Directory.Delete(directory, true), TimeSpan.FromSeconds(1), 5);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
foreach (var mdfile in Directory.GetFiles(folder, "*.md"))
|
||||
Retry.Do(() => File.Delete(mdfile), TimeSpan.FromSeconds(1), 5);
|
||||
}
|
||||
else
|
||||
{
|
||||
Directory.CreateDirectory(folder);
|
||||
}
|
||||
}
|
||||
|
||||
private readonly Events _events = new Events();
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
using System.IO;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Text.RegularExpressions;
|
||||
using MarkdownDeep;
|
||||
|
||||
@@ -11,6 +12,7 @@ namespace OurUmbraco.Documentation.Busineslogic
|
||||
public MarkdownLogic(string filePath)
|
||||
{
|
||||
_filePath = filePath;
|
||||
AppendAltLessonLink = false;
|
||||
}
|
||||
|
||||
public const string VersionSession = "DocumentationVersion";
|
||||
@@ -28,6 +30,8 @@ namespace OurUmbraco.Documentation.Busineslogic
|
||||
|
||||
public bool PrefixLinks { get; set; }
|
||||
|
||||
public bool AppendAltLessonLink { get; set; }
|
||||
|
||||
public string DoTransformation()
|
||||
{
|
||||
if (File.Exists(_filePath))
|
||||
@@ -79,6 +83,11 @@ namespace OurUmbraco.Documentation.Busineslogic
|
||||
else
|
||||
mdUrlTag.TrimEnd('/');
|
||||
|
||||
//Need to ensure we dont append the image links as they 404 if we add altTemplate
|
||||
if (AppendAltLessonLink && rawUrl.StartsWith("images/") == false)
|
||||
{
|
||||
return mdUrlTag.Replace(rawUrl, string.Format("{0}?altTemplate=Lesson", rawUrl.EnsureNoDotsInUrl()));
|
||||
}
|
||||
|
||||
return mdUrlTag.Replace(rawUrl, rawUrl.EnsureNoDotsInUrl());
|
||||
}
|
||||
|
||||
@@ -0,0 +1,280 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net;
|
||||
using System.Net.Http;
|
||||
using System.Web.Http;
|
||||
using OurUmbraco.Documentation.Busineslogic.GithubSourcePull;
|
||||
using OurUmbraco.Documentation.Models;
|
||||
using Umbraco.Core;
|
||||
using Umbraco.Web.Mvc;
|
||||
using Umbraco.Web.WebApi;
|
||||
using System.Web;
|
||||
using OurUmbraco.Documentation.Busineslogic;
|
||||
using System.Runtime.Serialization;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Converters;
|
||||
|
||||
namespace OurUmbraco.Documentation.Controllers
|
||||
{
|
||||
[PluginController("Documentation")]
|
||||
public class LessonsController : UmbracoApiController
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="path">The path in the documentation folder structure that you wish to start from & list descendants</param>
|
||||
/// <param name="userType">Future Use: Backoffice Usertype requesting lessons</param>
|
||||
/// <param name="allowedSections">Future Use: AllowedSections of BackOffice User</param>
|
||||
/// <param name="lang">Future Use: Backoffice Users langunage</param>
|
||||
/// <param name="version">Umbraco CMS Version as a string</param>
|
||||
/// <returns>
|
||||
/// A partial part of the documentation tree, that lists out folders
|
||||
/// This is used in the new Starter Kit in conjuction with 'Lessons'
|
||||
/// </returns>
|
||||
public List<ZipDownloader.SiteMapItem> GetDocsForPath(string path, string userType, string allowedSections, string lang, string version)
|
||||
{
|
||||
//Ensure path is not null & empty
|
||||
if (string.IsNullOrEmpty(path))
|
||||
{
|
||||
var resp = new HttpResponseMessage(HttpStatusCode.BadRequest)
|
||||
{
|
||||
Content = new StringContent("Path varibale is null or empty"),
|
||||
ReasonPhrase = "Documentation Path is invalid"
|
||||
};
|
||||
|
||||
throw new HttpResponseException(resp);
|
||||
}
|
||||
|
||||
//Get the documentation Sitemap JS file that lives on disk everytime we fetch & unpack the markdown docs from GitHub
|
||||
var docs = new ZipDownloader();
|
||||
|
||||
//Note: For now the folder param is NOT the folder/subtree but where the JSON file is stored to build up this model
|
||||
var allDocs = docs.DocumentationSiteMap();
|
||||
|
||||
|
||||
//Split path and ensure we can find each part of the path
|
||||
//In the array of nested objects
|
||||
var pathArray = path.Split('/').Where(x => string.IsNullOrEmpty(x) == false).ToArray();
|
||||
var currentDirectory = allDocs;
|
||||
|
||||
for (int i = 0; i < pathArray.Length; i++)
|
||||
{
|
||||
var pathPart = "/" + string.Join("/", pathArray.Take(i + 1));
|
||||
currentDirectory = currentDirectory.directories.First(x => x.path == pathPart);
|
||||
}
|
||||
|
||||
return currentDirectory.directories.OrderBy(x=> x.sort).ToList();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets Steps (Children of a lesson as rendered HTML from the markdown file)
|
||||
/// </summary>
|
||||
/// <param name="path"></param>
|
||||
/// <returns></returns>
|
||||
public List<LessonStep> GetStepsForPath(string path)
|
||||
{
|
||||
var docs = new ZipDownloader();
|
||||
var rootFolder = global::Umbraco.Core.IO.IOHelper.MapPath("/Documentation/" + path);
|
||||
var mdFiles = System.IO.Directory.GetFiles(rootFolder, "*.md");
|
||||
|
||||
var result = new List<LessonStep>();
|
||||
foreach(var fpath in mdFiles)
|
||||
{
|
||||
var content = System.IO.File.ReadAllText(fpath);
|
||||
var name = System.IO.Path.GetFileName(path);
|
||||
var md = new MarkdownLogic(fpath);
|
||||
var html = md.DoTransformation();
|
||||
|
||||
result.Add(new LessonStep() { Name = name, Content = html });
|
||||
}
|
||||
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="sectionAlias"></param>
|
||||
/// <param name="treeAlias"></param>
|
||||
public List<HelpDocument> GetContextHelpDocs(string sectionAlias, string treeAlias)
|
||||
{
|
||||
if (sectionAlias.ToLower() == "settings" && treeAlias.ToLower() == "documenttypes")
|
||||
{
|
||||
return new List<HelpDocument>
|
||||
{
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Defining Content",
|
||||
Description = "Here you'll find an explanation of how content is defined and quick guide for your first go at it (based on an empty installation).",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Data/Defining-content/"
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
if (sectionAlias.ToLower() == "settings" && (treeAlias.ToLower() == "templates" || treeAlias.ToLower() == "partialviews") )
|
||||
{
|
||||
return new List<HelpDocument>
|
||||
{
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Templates",
|
||||
Description = "Templating in Umbraco builds on the concept of Razor Views from asp.net MVC - if you already know this, then you are ready to create your first template - if not, this is a quick and handy guide.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Design/Templates/"
|
||||
},
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Basic Razor Syntax",
|
||||
Description = "Shows how to perform common logical tasks in Razor like if/else, foreach loops, switch statements and using the @ character to separate code and markup.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Design/Templates/basic-razor-syntax"
|
||||
},
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Rendering Content",
|
||||
Description = "The primary task of any template in Umbraco is to render the values of the current page or the result of query against the content cache.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Design/Rendering-Content/"
|
||||
},
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Rendering Media",
|
||||
Description = "Templates can access items in the Media library, to assist in displaying rich content like galleries.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Design/Rendering-Media/"
|
||||
},
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Basic Razor Syntax",
|
||||
Description = "Shows how to perform common logical tasks in Razor like if/else, foreach loops, switch statements and using the @ character to separate code and markup.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Design/Templates/basic-razor-syntax"
|
||||
},
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "View/Razor Examples",
|
||||
Description = "Lots of examples of using various techniques to render data in a view",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Reference/Templating/Mvc/examples"
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
if (sectionAlias.ToLower() == "media")
|
||||
{
|
||||
return new List<HelpDocument>
|
||||
{
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Creating Media",
|
||||
Description = "Media in Umbraco is handled in much the same way as content. Instead of defining Document Types you define Media Types that act as the base for media items.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Data/Creating-Media/"
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
if (sectionAlias.ToLower() == "developer" && treeAlias.ToLower() == "datatypes")
|
||||
{
|
||||
return new List<HelpDocument>
|
||||
{
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Data-Types",
|
||||
Description = "A Data Type defines the type of input for a property. So when adding a property (on Document Types, Media Types and Members) when selecting the Type you are selecting a Data Type. There are a number of preconfigured Data Types available in Umbraco and more can be added in the Developer section.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Data/Data-Types/"
|
||||
},
|
||||
|
||||
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Property Editors",
|
||||
Description = "Extend Umbraco with your own property editors ",
|
||||
Url = "https://our.umbraco.org/documentation/Extending/Property-Editors/",
|
||||
Type = HelpDocType.Doc
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
if (sectionAlias.ToLower() == "member")
|
||||
{
|
||||
return new List<HelpDocument>
|
||||
{
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Members",
|
||||
Description = "Members are used for registering and authenticating external users of an Umbraco installation (ie. forum members, intranet users and so forth). Unlike with Document Types and Media Types everything is done in the Members section both defining and creating, and editing members.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Data/Members/"
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
if (sectionAlias.ToLower() == "developer")
|
||||
{
|
||||
return new List<HelpDocument>
|
||||
{
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Data-Types",
|
||||
Description = "A Data Type defines the type of input for a property. So when adding a property (on Document Types, Media Types and Members) when selecting the Type you are selecting a Data Type. There are a number of preconfigured Data Types available in Umbraco and more can be added in the Developer section.",
|
||||
Type = HelpDocType.Doc,
|
||||
Url = "https://our.umbraco.org/documentation/Getting-Started/Data/Data-Types/"
|
||||
},
|
||||
|
||||
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Macros",
|
||||
Description = "A macro is a reusable piece of functionality that you can re-use throughout your site. Macros can be configured with parameters and be inserted into a Rich Text Editor.",
|
||||
Url = "https://our.umbraco.org/Documentation/Reference/Templating/Macros/",
|
||||
Type = HelpDocType.Doc
|
||||
},
|
||||
|
||||
new HelpDocument
|
||||
{
|
||||
Name = "Xslt",
|
||||
Description = "XSLT will soon be removed from Umbraco - read how you can transition away from it",
|
||||
Url = "https://our.umbraco.org/Documentation/Reference/Templating/Macros/Xslt/",
|
||||
Type = HelpDocType.Doc
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
//Did not find anything for the combination
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
[DataContract(Name = "lessonStep")]
|
||||
public class LessonStep
|
||||
{
|
||||
[DataMember(Name = "name")]
|
||||
public string Name { get; set; }
|
||||
|
||||
[DataMember(Name = "content")]
|
||||
public string Content { get; set; }
|
||||
}
|
||||
|
||||
[DataContract(Name = "helpDocument")]
|
||||
public class HelpDocument
|
||||
{
|
||||
[DataMember(Name = "name")]
|
||||
public string Name { get; set; }
|
||||
|
||||
[DataMember(Name = "url")]
|
||||
public string Url { get; set; }
|
||||
|
||||
[DataMember(Name = "description")]
|
||||
public string Description { get; set; }
|
||||
|
||||
[DataMember(Name = "type")]
|
||||
[JsonConverter(typeof(StringEnumConverter))]
|
||||
public HelpDocType Type { get; set; }
|
||||
}
|
||||
|
||||
public enum HelpDocType { Doc, Video }
|
||||
}
|
||||
@@ -5,6 +5,8 @@ using System.Web;
|
||||
using OurUmbraco.Documentation.Busineslogic;
|
||||
using Umbraco.Core;
|
||||
using Umbraco.Web.Routing;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
|
||||
namespace OurUmbraco.Documentation
|
||||
{
|
||||
@@ -29,7 +31,7 @@ namespace OurUmbraco.Documentation
|
||||
return false;
|
||||
|
||||
// kill those old urls
|
||||
foreach (var s in new []{ "master", "v480" })
|
||||
foreach (var s in new[] { "master", "v480" })
|
||||
if (url.StartsWith(mdRoot + "/" + s))
|
||||
{
|
||||
url = url.Replace(mdRoot + "/" + s, mdRoot);
|
||||
@@ -39,7 +41,7 @@ namespace OurUmbraco.Documentation
|
||||
|
||||
// find the md file
|
||||
var mdFilepath = FindMarkdownFile(url);
|
||||
|
||||
|
||||
//return the broken link doc page
|
||||
var is404 = false;
|
||||
if (mdFilepath == null)
|
||||
@@ -48,13 +50,13 @@ namespace OurUmbraco.Documentation
|
||||
is404 = true;
|
||||
}
|
||||
if (mdFilepath == null)
|
||||
{
|
||||
{
|
||||
// clear the published content (that was set by FindContent) to cause a 404, and in
|
||||
// both case return 'true' because there's no point other finders try to handle the request
|
||||
contentRequest.PublishedContent = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
if (is404) contentRequest.SetIs404();
|
||||
|
||||
// set the context vars
|
||||
@@ -70,7 +72,7 @@ namespace OurUmbraco.Documentation
|
||||
var templateIsSet = contentRequest.TrySetTemplate(altTemplate);
|
||||
//httpContext.Trace.Write("Markdown Files Handler",
|
||||
// string.Format("Template changed to: '{0}' is {1}", altTemplate, templateIsSet));
|
||||
|
||||
|
||||
// be happy
|
||||
return true;
|
||||
}
|
||||
@@ -113,7 +115,7 @@ namespace OurUmbraco.Documentation
|
||||
fpath = string.Concat(HttpRuntime.AppDomainAppPath, relpath, "\\index.md");
|
||||
if (File.Exists(fpath))
|
||||
return fpath;
|
||||
|
||||
|
||||
fpath = string.Concat(HttpRuntime.AppDomainAppPath, relpath, "\\readme.md");
|
||||
if (File.Exists(fpath))
|
||||
return fpath;
|
||||
@@ -145,37 +147,94 @@ namespace OurUmbraco.Documentation
|
||||
string baseUrl = "https://github.com/umbraco/UmbracoDocs/blob/" + branchName;
|
||||
|
||||
var docUrl = HttpContext.Current.Items[MarkdownLogic.MarkdownPathKey].ToString();
|
||||
|
||||
if (System.IO.File.Exists(docUrl))
|
||||
|
||||
//Need to get NEW key as needs to be the original MD filename
|
||||
//from Github including .md & correct casing of file
|
||||
//var originalUrl = HttpContext.Current.Items["umbOriginalUrl"].ToString();
|
||||
string originalUrl;
|
||||
if (!TryGetExactPath(docUrl, out originalUrl))
|
||||
{
|
||||
//Need to get NEW key as needs to be the original MD filename
|
||||
//from Github including .md & correct casing of file
|
||||
var originalUrl = HttpContext.Current.Items["umbOriginalUrl"].ToString();
|
||||
|
||||
//Ensure beginning part of url is right case for GitHub URL
|
||||
if (originalUrl.StartsWith("/documentation/", StringComparison.InvariantCultureIgnoreCase))
|
||||
// don't strip off the leading "/"
|
||||
originalUrl = originalUrl.Substring("/documentation/".Length - 1);
|
||||
|
||||
//If ends with / then it's an index.md file in a folder
|
||||
if (originalUrl.EndsWith("/"))
|
||||
{
|
||||
//Add the word after the /, so it's /index
|
||||
originalUrl += "index";
|
||||
|
||||
}
|
||||
|
||||
//Append the .md file extension
|
||||
docUrl = baseUrl + string.Format("{0}{1}", originalUrl, ".md");
|
||||
|
||||
// MD file does not exist on disk - hide edit button
|
||||
return null;
|
||||
}
|
||||
else
|
||||
|
||||
// Ensure beginning part of url is right case for GitHub URL
|
||||
var docFolderPosition = originalUrl.IndexOf(@"\documentation\", StringComparison.InvariantCultureIgnoreCase);
|
||||
if (docFolderPosition > -1)
|
||||
{
|
||||
//MD file does not exist on disk - hide edit button
|
||||
docUrl = null;
|
||||
// don't strip off the leading "/"
|
||||
originalUrl = originalUrl
|
||||
.Substring(docFolderPosition + @"\documentation\".Length - 1)
|
||||
.Replace('\\', '/');
|
||||
}
|
||||
|
||||
// If ends with / then it's an index.md file in a folder
|
||||
if (originalUrl.EndsWith("/"))
|
||||
{
|
||||
// Add the word after the /, so it's /index
|
||||
originalUrl += "index.md";
|
||||
}
|
||||
|
||||
// Append the base and file url together
|
||||
docUrl = baseUrl + originalUrl;
|
||||
|
||||
|
||||
|
||||
return docUrl;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the exact case used on the file system for an existing file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">A relative or absolute path.</param>
|
||||
/// <param name="exactPath">The full path using the correct case if the path exists. Otherwise, null.</param>
|
||||
/// <returns>True if the exact path was found. False otherwise.</returns>
|
||||
/// <remarks>
|
||||
/// This supports drive-lettered paths and UNC paths, but a UNC root
|
||||
/// will be returned in title case (e.g., \\Server\Share).
|
||||
/// Original from http://stackoverflow.com/a/29578292/97615
|
||||
/// </remarks>
|
||||
public static bool TryGetExactPath(string path, out string exactPath)
|
||||
{
|
||||
bool result = false;
|
||||
exactPath = null;
|
||||
|
||||
// DirectoryInfo accepts either a file path or a directory path, and most of its properties work for either.
|
||||
// However, its Exists property only works for a directory path.
|
||||
DirectoryInfo directory = new DirectoryInfo(path);
|
||||
if (File.Exists(path) || directory.Exists)
|
||||
{
|
||||
var parts = new List<string>();
|
||||
|
||||
DirectoryInfo parentDirectory = directory.Parent;
|
||||
while (parentDirectory != null)
|
||||
{
|
||||
FileSystemInfo entry = parentDirectory.EnumerateFileSystemInfos(directory.Name).First();
|
||||
parts.Add(entry.Name);
|
||||
|
||||
directory = parentDirectory;
|
||||
parentDirectory = directory.Parent;
|
||||
}
|
||||
|
||||
// Handle the root part (i.e., drive letter or UNC \\server\share).
|
||||
string root = directory.FullName;
|
||||
if (root.Contains(':'))
|
||||
{
|
||||
root = root.ToUpper();
|
||||
}
|
||||
else
|
||||
{
|
||||
string[] rootParts = root.Split('\\');
|
||||
root = string.Join("\\", rootParts.Select(part => CultureInfo.CurrentCulture.TextInfo.ToTitleCase(part)));
|
||||
}
|
||||
|
||||
parts.Add(root);
|
||||
parts.Reverse();
|
||||
exactPath = Path.Combine(parts.ToArray());
|
||||
result = true;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -123,7 +123,7 @@ FETCH NEXT @count ROWS ONLY";
|
||||
/// </summary>
|
||||
/// <param name="category"></param>
|
||||
/// <returns></returns>
|
||||
public int GetAllTopicsCount(int category = -1)
|
||||
public int GetAllTopicsCount(int category = -1, bool unsolved = false, bool noreplies = false)
|
||||
{
|
||||
const string sql1 = @"SELECT COUNT(*) as forumTopicCount
|
||||
FROM forumTopics
|
||||
@@ -135,6 +135,18 @@ LEFT OUTER JOIN umbracoNode u2 ON (forumTopics.memberId = u2.id AND u2.nodeObjec
|
||||
|
||||
var sql = (category > 0 ? sqlic : sqlix);
|
||||
|
||||
if (unsolved)
|
||||
if (sql.Contains("WHERE"))
|
||||
sql = sql + " AND answer = 0";
|
||||
else
|
||||
sql = sql + " WHERE answer = 0";
|
||||
|
||||
if (noreplies)
|
||||
if (sql.Contains("WHERE"))
|
||||
sql = sql + " AND replies = 0";
|
||||
else
|
||||
sql = sql + " WHERE replies = 0";
|
||||
|
||||
return _databaseContext.Database.ExecuteScalar<int>(sql, new { category = category });
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
using System.Collections.Generic;
|
||||
using OurUmbraco.Community.Models;
|
||||
using RestSharp;
|
||||
|
||||
namespace OurUmbraco.Our.Api
|
||||
{
|
||||
public class GitHubController
|
||||
{
|
||||
private const string RepositoryOwner = "Umbraco";
|
||||
private const string GitHubApiClient = "https://api.github.com";
|
||||
private const string UserAgent = "OurUmbraco";
|
||||
|
||||
/// <summary>
|
||||
/// Get all contributors from GitHub Umbraco repositories
|
||||
/// </summary>
|
||||
/// <param name="repo"></param>
|
||||
/// <returns></returns>
|
||||
public IRestResponse<List<GitHubContributorModel>> GetAllRepoContributors(string repo)
|
||||
{
|
||||
var client = new RestClient(GitHubApiClient);
|
||||
var request = new RestRequest(string.Format("/repos/{0}/{1}/stats/contributors", RepositoryOwner, repo), Method.GET);
|
||||
client.UserAgent = UserAgent;
|
||||
var response = client.Execute<List<GitHubContributorModel>>(request);
|
||||
return response;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -241,6 +241,18 @@
|
||||
<HintPath>..\packages\semver.1.1.2\lib\net451\Semver.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="Skybrud.Essentials, Version=1.0.8.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\Skybrud.Essentials.1.0.8\lib\net45\Skybrud.Essentials.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="Skybrud.Social.Core">
|
||||
<HintPath>..\packages\Skybrud.Social.Core.1.0.0-beta9\lib\net45\Skybrud.Social.Core.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="Skybrud.Social.Meetup, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\Skybrud.Social.Meetup.1.0.0-beta002\lib\net45\Skybrud.Social.Meetup.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
</Reference>
|
||||
<Reference Include="SQLCE4Umbraco, Version=1.0.6261.14294, Culture=neutral, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\UmbracoCms.Core.7.5.10\lib\SQLCE4Umbraco.dll</HintPath>
|
||||
<Private>True</Private>
|
||||
@@ -391,7 +403,16 @@
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="CamelCaseFormatter.cs" />
|
||||
<Compile Include="Community\Controllers\GitHubContributorController.cs" />
|
||||
<Compile Include="Community\Controllers\MeetupsController.cs" />
|
||||
<Compile Include="Community\Controllers\GitHubGlobalContributorModel.cs" />
|
||||
<Compile Include="Community\Controllers\TwitterSearchController.cs" />
|
||||
<Compile Include="Community\Models\GitHubContributorModel.cs" />
|
||||
<Compile Include="Community\Models\IGitHubContributorModel.cs" />
|
||||
<Compile Include="Community\Models\MeetupEventsModel.cs" />
|
||||
<Compile Include="Community\Models\MeetupItem.cs" />
|
||||
<Compile Include="Community\Models\GitHubContributorsModel.cs" />
|
||||
<Compile Include="Community\Models\IGitHubContributorsModel.cs" />
|
||||
<Compile Include="Community\Models\TweetsModel.cs" />
|
||||
<Compile Include="CustomDateTimeConvertor.cs" />
|
||||
<Compile Include="Documentation\Busineslogic\ConventionExtensions.cs" />
|
||||
@@ -401,6 +422,7 @@
|
||||
<Compile Include="Documentation\Busineslogic\GithubSourcePull\ZipDownloader.cs" />
|
||||
<Compile Include="Documentation\Busineslogic\MarkdownLogic.cs" />
|
||||
<Compile Include="Documentation\Controllers\AppVeyorAuthorizeFilterAttribute.cs" />
|
||||
<Compile Include="Documentation\Controllers\LessonsController.cs" />
|
||||
<Compile Include="Documentation\Models\Artifact.cs" />
|
||||
<Compile Include="Documentation\Models\Compilationmessage.cs" />
|
||||
<Compile Include="Documentation\Models\DocFxUpdateModel.cs" />
|
||||
@@ -504,6 +526,7 @@
|
||||
<Compile Include="NotificationsWeb\Services\NotificationService.cs" />
|
||||
<Compile Include="NotificationsWeb\Singleton.cs" />
|
||||
<Compile Include="Our\Api\CommunityController.cs" />
|
||||
<Compile Include="Our\Api\GitHubController.cs" />
|
||||
<Compile Include="Our\Api\SearchController.cs" />
|
||||
<Compile Include="Our\Api\YouTrackApiController.cs" />
|
||||
<Compile Include="Our\Businesslogic\ProjectContributor.cs" />
|
||||
|
||||
@@ -60,6 +60,16 @@ namespace OurUmbraco.Repository.Controllers
|
||||
var starterKits = new List<StarterKit>();
|
||||
var allConfiguredVersions = UWikiFileVersion.GetAllVersions();
|
||||
|
||||
// for 7.6.4+ we change behavior and only provide one starter kit
|
||||
if (version >= new System.Version(7, 6, 4))
|
||||
{
|
||||
officialStarterKitGuidCollection = new List<string>
|
||||
{
|
||||
ConfigurationManager.AppSettings["UmbracoStarterKitDefault"]
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
foreach (var umbracoNode in umbracoNodes)
|
||||
{
|
||||
// If it's not in the official list, move on to the next package
|
||||
|
||||
@@ -230,6 +230,8 @@ namespace OurUmbraco.Repository.Services
|
||||
|
||||
//get the strict packages in the correct desc order
|
||||
var strictPackageFileVersions = GetAllStrictSupportedPackageVersions(allPackageFiles).ToArray();
|
||||
//these are ordered by package version desc
|
||||
var nonStrictPackageFiles = GetNonStrictSupportedPackageVersions(allPackageFiles).ToArray();
|
||||
|
||||
var packageDetails = new PackageDetails(package)
|
||||
{
|
||||
@@ -259,31 +261,7 @@ namespace OurUmbraco.Repository.Services
|
||||
else if (currentUmbracoVersion < version75)
|
||||
{
|
||||
//if the umbraco version is < 7.5 it means that strict package formats are not supported
|
||||
|
||||
//TODO: Now we have to do the opposite of below and filter out any package file versions that have strict
|
||||
// umbraco dependencies applied. Anything that has 7.5 (which would be the very minimum strict dependency) we can check for
|
||||
|
||||
//these are ordered by package version desc
|
||||
var nonStrictPackageFiles = GetNonStrictSupportedPackageVersions(allPackageFiles).ToArray();
|
||||
|
||||
if (nonStrictPackageFiles.Length != 0)
|
||||
{
|
||||
//there might be a case where the 'current release file' is not the latest version found, so let's check if
|
||||
//the latest release file is included in the non-strict packages and if so we'll use that, otherwise we'll use the latest
|
||||
var found = nonStrictPackageFiles.FirstOrDefault(x => x.FileId == currentReleaseFile);
|
||||
if (found != null)
|
||||
{
|
||||
//it's included in the non strict packages so use it
|
||||
packageDetails.ZipUrl = string.Concat(BASE_URL, "/FileDownload?id=", currentReleaseFile);
|
||||
packageDetails.ZipFileId = currentReleaseFile;
|
||||
}
|
||||
else
|
||||
{
|
||||
//use the latest available package version
|
||||
packageDetails.ZipUrl = string.Concat(BASE_URL, "/FileDownload?id=", nonStrictPackageFiles[0].FileId);
|
||||
packageDetails.ZipFileId = nonStrictPackageFiles[0].FileId;
|
||||
}
|
||||
}
|
||||
AssignLatestNonStrictPackageFile(nonStrictPackageFiles, currentReleaseFile, packageDetails);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -307,7 +285,15 @@ namespace OurUmbraco.Repository.Services
|
||||
//got one! so use it's id for the file download
|
||||
packageDetails.ZipUrl = string.Concat(BASE_URL, "/FileDownload?id=", found);
|
||||
packageDetails.ZipFileId = found;
|
||||
}
|
||||
}
|
||||
else if (nonStrictPackageFiles.Length > 0)
|
||||
{
|
||||
//Here's the other case, if this package has both strict and non-strict package file versions and we didn't find one above,
|
||||
//than we need to determine if the latest non-strict package file format should be used for the current version being passed in
|
||||
|
||||
AssignLatestNonStrictPackageFile(nonStrictPackageFiles, currentReleaseFile, packageDetails);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
packageDetails.Created = content.CreateDate;
|
||||
@@ -315,6 +301,28 @@ namespace OurUmbraco.Repository.Services
|
||||
return packageDetails;
|
||||
}
|
||||
|
||||
private void AssignLatestNonStrictPackageFile(PackageVersionSupport[] nonStrictPackageFiles, int currentReleaseFile, PackageDetails packageDetails)
|
||||
{
|
||||
if (nonStrictPackageFiles.Length > 0)
|
||||
{
|
||||
//there might be a case where the 'current release file' is not the latest version found, so let's check if
|
||||
//the latest release file is included in the non-strict packages and if so we'll use that, otherwise we'll use the latest
|
||||
var found = nonStrictPackageFiles.FirstOrDefault(x => x.FileId == currentReleaseFile);
|
||||
if (found != null)
|
||||
{
|
||||
//it's included in the non strict packages so use it
|
||||
packageDetails.ZipUrl = string.Concat(BASE_URL, "/FileDownload?id=", currentReleaseFile);
|
||||
packageDetails.ZipFileId = currentReleaseFile;
|
||||
}
|
||||
else
|
||||
{
|
||||
//use the latest available package version
|
||||
packageDetails.ZipUrl = string.Concat(BASE_URL, "/FileDownload?id=", nonStrictPackageFiles[0].FileId);
|
||||
packageDetails.ZipFileId = nonStrictPackageFiles[0].FileId;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private List<PackageCompatibility> GetPackageCompatibility(IPublishedContent content)
|
||||
{
|
||||
var service = new VersionCompatibilityService(DatabaseContext);
|
||||
@@ -365,6 +373,8 @@ namespace OurUmbraco.Repository.Services
|
||||
.Where(x => x.PackageVersion != null && x.MinUmbracoVersion != null)
|
||||
.OrderByDescending(x => x.PackageVersion)
|
||||
.ThenByDescending(x => x.MinUmbracoVersion)
|
||||
//need to sort by latest file Id too since multiple files can target the same umbraco versions but we want to take the latest uploaded file
|
||||
.ThenByDescending(x => x.FileId)
|
||||
.ToArray();
|
||||
return allVersions;
|
||||
}
|
||||
@@ -384,6 +394,8 @@ namespace OurUmbraco.Repository.Services
|
||||
.Select(x => new PackageVersionSupport(x.Id, x.Version.Version.GetFromUmbracoString(reduceToConfigured:false), null))
|
||||
.Where(x => x.PackageVersion != null)
|
||||
.OrderByDescending(x => x.PackageVersion)
|
||||
//need to sort by latest file Id too since multiple files can target the same umbraco versions but we want to take the latest uploaded file
|
||||
.ThenByDescending(x => x.FileId)
|
||||
.ToArray();
|
||||
return allVersions;
|
||||
}
|
||||
|
||||
@@ -415,11 +415,12 @@ namespace OurUmbraco.Wiki.BusinessLogic
|
||||
public static List<UmbracoVersion> GetVersionsFromString(string p)
|
||||
{
|
||||
var umbracoVersions = new List<UmbracoVersion>();
|
||||
var availableVersions = UmbracoVersion.AvailableVersions();
|
||||
|
||||
foreach (var ver in p.Split(','))
|
||||
{
|
||||
if (UmbracoVersion.AvailableVersions().ContainsKey(ver))
|
||||
umbracoVersions.Add(UmbracoVersion.AvailableVersions()[ver]);
|
||||
if (availableVersions.ContainsKey(ver))
|
||||
umbracoVersions.Add(availableVersions[ver]);
|
||||
}
|
||||
|
||||
return umbracoVersions;
|
||||
|
||||
@@ -55,6 +55,9 @@
|
||||
<package id="RestSharp" version="104.1" targetFramework="net451" />
|
||||
<package id="semver" version="1.1.2" targetFramework="net452" />
|
||||
<package id="SharpZipLib" version="0.86.0" targetFramework="net452" />
|
||||
<package id="Skybrud.Essentials" version="1.0.8" targetFramework="net452" />
|
||||
<package id="Skybrud.Social.Core" version="1.0.0-beta9" targetFramework="net452" />
|
||||
<package id="Skybrud.Social.Meetup" version="1.0.0-beta002" targetFramework="net452" />
|
||||
<package id="System.Collections" version="4.3.0" targetFramework="net452" />
|
||||
<package id="System.Collections.Concurrent" version="4.3.0" targetFramework="net452" />
|
||||
<package id="System.Diagnostics.Debug" version="4.3.0" targetFramework="net452" />
|
||||
|
||||
+27
-14
@@ -1,11 +1,16 @@
|
||||
@ECHO OFF
|
||||
SETLOCAL
|
||||
:: SETLOCAL is on, so changes to the path not persist to the actual user's path
|
||||
|
||||
|
||||
SET release=%1
|
||||
SET toolsFolder=%CD%\tools\
|
||||
ECHO Installing Npm NuGet Package
|
||||
|
||||
SET nuGetFolder=%CD%\..\packages\
|
||||
ECHO Configured packages folder: %nuGetFolder%
|
||||
ECHO Current folder: %CD%
|
||||
|
||||
%CD%\tools\nuget.exe install Npm.js -OutputDirectory %nuGetFolder% -Verbosity quiet
|
||||
|
||||
SET toolsFolder=%CD%\tools
|
||||
SET nodeFileName=node-v4.5.0-win-x86.7z
|
||||
SET nodeExtractFolder=%toolsFolder%node.js.450
|
||||
IF NOT EXIST %nodeExtractFolder% (
|
||||
@@ -16,10 +21,21 @@ IF NOT EXIST %nodeExtractFolder% (
|
||||
)
|
||||
FOR /f "delims=" %%A in ('dir %nodeExtractFolder%\node* /b') DO SET "nodePath=%nodeExtractFolder%\%%A"
|
||||
|
||||
FOR /f "delims=" %%A in ('dir %nuGetFolder%node.js.* /b') do set "nodePath=%nuGetFolder%%%A\"
|
||||
FOR /f "delims=" %%A in ('dir %nuGetFolder%npm.js.* /b') do set "npmPath=%nuGetFolder%%%A\tools\"
|
||||
|
||||
ECHO Adding Npm and Node to path
|
||||
REM SETLOCAL is on, so changes to the path not persist to the actual user's path
|
||||
PATH=%npmPath%;%nodePath%;%PATH%
|
||||
|
||||
SET buildFolder=%CD%
|
||||
|
||||
ECHO Change directory to %CD%\..\OurUmbraco.Client\
|
||||
CD %CD%\..\OurUmbraco.Client\
|
||||
|
||||
SET nuGetFolder=%CD%\..\packages\
|
||||
FOR /f "delims=" %%A in ('dir %nuGetFolder%npm.js.* /b') DO SET "npmPath=%nuGetFolder%%%A\tools\"
|
||||
IF [%npmPath%] == [] GOTO :installnpm
|
||||
IF NOT [%npmPath%] == [] GOTO :build
|
||||
|
||||
:installnpm
|
||||
ECHO Downloading npm
|
||||
@@ -31,19 +47,16 @@ IF NOT [%npmPath%] == [] GOTO :build
|
||||
GOTO :build
|
||||
|
||||
:build
|
||||
ECHO Gulp build the client side files
|
||||
|
||||
PATH=%npmPath%;%nodePath%
|
||||
SET buildFolder=%CD%
|
||||
|
||||
ECHO Change directory to %CD%\..\OurUmbraco.Client\
|
||||
CD %CD%\..\OurUmbraco.Client\
|
||||
|
||||
ECHO Do npm install and the gulp build
|
||||
SET npm="%nodePath%\node.exe" "%npmPath%node_modules\npm\bin\npm-cli.js" %*
|
||||
%npm% cache clean
|
||||
|
||||
%npm% install
|
||||
%npm% install --save-dev jshint gulp-jshint
|
||||
%npm% install -g install gulp -g
|
||||
gulp
|
||||
gulp build
|
||||
|
||||
|
||||
ECHO Move back to the build folder
|
||||
CD %buildFolder%
|
||||
GOTO :EOF
|
||||
CD %buildFolder%
|
||||
Binary file not shown.
Reference in New Issue
Block a user