├── .editorconfig
├── .gitignore
├── .jshintrc
├── .meteor
├── .finished-upgraders
├── .gitignore
├── .id
├── cordova-plugins
├── packages
├── platforms
├── release
└── versions
├── .travis.yml
├── History.md
├── README.md
├── README.nitrous.md
├── Roadmap.md
├── app-graphics
├── telescope-128.png
├── telescope-150.png
├── telescope-24.png
├── telescope-256.png
├── telescope-300.png
└── telescope-48.png
├── client
├── helpers
│ └── handlebars.js
├── main.html
├── main.js
└── views
│ ├── admin
│ ├── settings_form.html
│ └── settings_form.js
│ ├── comments
│ ├── comment_deleted.html
│ ├── comment_edit.html
│ ├── comment_edit.js
│ ├── comment_form.html
│ ├── comment_form.js
│ ├── comment_item.html
│ ├── comment_item.js
│ ├── comment_list.html
│ ├── comment_list.js
│ ├── comment_reply.html
│ └── comment_reply.js
│ ├── common
│ ├── css.html
│ ├── css.js
│ ├── footer.html
│ ├── footer.js
│ ├── layout.html
│ ├── layout.js
│ ├── message_item.html
│ ├── message_item.js
│ ├── messages.html
│ └── messages.js
│ ├── errors
│ ├── already_logged_in.html
│ ├── loading.html
│ ├── loading.js
│ ├── no_account.html
│ ├── no_account.js
│ ├── no_invite.html
│ ├── no_invite.js
│ ├── no_rights.html
│ └── not_found.html
│ ├── forms
│ ├── quickFormTelescope.html
│ ├── quickFormTelescope.js
│ ├── urlCustomType.html
│ └── urlCustomType.js
│ ├── nav
│ ├── admin_menu.html
│ ├── admin_menu.js
│ ├── menu_item.html
│ ├── mobile_nav.html
│ ├── mobile_nav.js
│ ├── nav.html
│ ├── nav.js
│ ├── submit_button.html
│ ├── user_menu.html
│ ├── user_menu.js
│ ├── views_menu.html
│ └── views_menu.js
│ ├── posts
│ ├── after_post_item.html
│ ├── before_post_item.html
│ ├── modules
│ │ ├── post_actions.html
│ │ ├── post_actions.js
│ │ ├── post_admin.html
│ │ ├── post_admin.js
│ │ ├── post_author.html
│ │ ├── post_avatars.html
│ │ ├── post_avatars.js
│ │ ├── post_comments_link.html
│ │ ├── post_content.html
│ │ ├── post_content.js
│ │ ├── post_discuss.html
│ │ ├── post_domain.html
│ │ ├── post_domain.js
│ │ ├── post_info.html
│ │ ├── post_info.js
│ │ ├── post_rank.html
│ │ ├── post_rank.js
│ │ ├── post_title.html
│ │ ├── post_title.js
│ │ ├── post_upvote.html
│ │ └── post_upvote.js
│ ├── post_body.html
│ ├── post_edit.html
│ ├── post_edit.js
│ ├── post_item.html
│ ├── post_item.js
│ ├── post_list
│ │ ├── posts_list.html
│ │ ├── posts_list.js
│ │ ├── posts_list_incoming.html
│ │ ├── posts_list_incoming.js
│ │ ├── posts_load_more.html
│ │ └── posts_load_more.js
│ ├── post_page.html
│ ├── post_page.js
│ ├── post_submit.html
│ └── post_submit.js
│ └── users
│ ├── account
│ ├── user_account.html
│ └── user_account.js
│ ├── profile
│ ├── user_comments.html
│ ├── user_comments.js
│ ├── user_downvoted_posts.html
│ ├── user_downvoted_posts.js
│ ├── user_info.html
│ ├── user_info.js
│ ├── user_posts.html
│ ├── user_posts.js
│ ├── user_upvoted_posts.html
│ └── user_upvoted_posts.js
│ ├── sandstorm_sign_in.html
│ ├── sign_out.html
│ ├── user_edit.html
│ ├── user_edit.js
│ ├── user_email.html
│ ├── user_email.js
│ ├── user_item.html
│ ├── user_item.js
│ ├── user_profile.html
│ ├── user_profile.js
│ ├── users.html
│ └── users.js
├── collections
├── comments.js
├── events.js
├── messages.js
├── posts.js
├── settings.js
└── users.js
├── i18n
├── bg.i18n.json
├── de.i18n.json
├── en.i18n.json
├── es.i18n.json
├── fr.i18n.json
├── it.i18n.json
├── ru.i18n.json
├── tr.i18n.json
└── zh-CN.i18n.json
├── lib
├── analytics.js
├── config
│ ├── at_config.js
│ ├── avatar.js
│ └── debug.js
├── debug.js
├── events.js
├── helpers.js
├── parameters.js
├── publications.js
├── router
│ ├── comments.js
│ ├── config.js
│ ├── filters.js
│ ├── other.js
│ ├── posts.js
│ ├── server.js
│ └── users.js
├── scoring.js
├── users.js
├── version.js
└── vote.js
├── license.md
├── packages.json
├── packages
├── .gitignore
├── npm-container
│ ├── .gitignore
│ ├── index.js
│ ├── package.js
│ └── versions.json
├── telescope-api
│ ├── .gitignore
│ ├── lib
│ │ └── server
│ │ │ ├── api.js
│ │ │ └── routes.js
│ ├── package.js
│ └── versions.json
├── telescope-base
│ ├── .gitignore
│ ├── lib
│ │ ├── base.js
│ │ ├── base_client.js
│ │ └── base_server.js
│ ├── package.js
│ └── versions.json
├── telescope-blank
│ ├── .gitignore
│ ├── i18n
│ │ └── en.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── stylesheets
│ │ │ │ └── custom.scss
│ │ │ └── templates
│ │ │ │ ├── customPostTitle.html
│ │ │ │ ├── custom_template.html
│ │ │ │ └── custom_template.js
│ │ ├── custom_fields.js
│ │ ├── hooks.js
│ │ ├── main.js
│ │ ├── routes.js
│ │ ├── server
│ │ │ └── publications.js
│ │ ├── settings.js
│ │ └── templates.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-daily
│ ├── .gitignore
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── stylesheets
│ │ │ │ └── daily.scss
│ │ │ └── templates
│ │ │ │ ├── after_day.html
│ │ │ │ ├── before_day.html
│ │ │ │ ├── posts_daily.html
│ │ │ │ └── posts_daily.js
│ │ ├── daily.js
│ │ └── routes.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-datetimepicker
│ ├── .gitignore
│ ├── autoform-bs-datetimepicker.html
│ ├── autoform-bs-datetimepicker.js
│ ├── bootstrap-collapse-transitions.js
│ ├── datetimepicker.scss
│ ├── fonts
│ │ ├── glyphicons-halflings-regular.eot
│ │ ├── glyphicons-halflings-regular.svg
│ │ ├── glyphicons-halflings-regular.ttf
│ │ └── glyphicons-halflings-regular.woff
│ ├── package.js
│ └── versions.json
├── telescope-email
│ ├── .gitignore
│ ├── .npm
│ │ └── package
│ │ │ ├── .gitignore
│ │ │ ├── README
│ │ │ └── npm-shrinkwrap.json
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ └── server
│ │ │ ├── email.js
│ │ │ ├── routes.js
│ │ │ └── templates
│ │ │ ├── emailAccountApproved.handlebars
│ │ │ ├── emailInvite.handlebars
│ │ │ ├── emailNewComment.handlebars
│ │ │ ├── emailNewPendingPost.handlebars
│ │ │ ├── emailNewPost.handlebars
│ │ │ ├── emailNewReply.handlebars
│ │ │ ├── emailNewUser.handlebars
│ │ │ ├── emailPostApproved.handlebars
│ │ │ ├── emailTest.handlebars
│ │ │ └── emailWrapper.handlebars
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-embedly
│ ├── .gitignore
│ ├── History.md
│ ├── README.md
│ ├── i18n
│ │ ├── en.i18n.json
│ │ └── fr.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── autoform-postthumbnail.html
│ │ │ ├── autoform-postthumbnail.js
│ │ │ ├── post_thumbnail.html
│ │ │ ├── post_thumbnail.js
│ │ │ ├── post_thumbnail.scss
│ │ │ ├── post_video.html
│ │ │ └── post_video.js
│ │ ├── embedly.js
│ │ └── server
│ │ │ └── get_embedly_data.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-getting-started
│ ├── .gitignore
│ ├── content
│ │ ├── customizing_telescope.md
│ │ ├── deploying_telescope.md
│ │ ├── getting_help.md
│ │ ├── images
│ │ │ ├── stackoverflow.png
│ │ │ └── telescope.png
│ │ ├── read_this_first.md
│ │ └── removing_getting_started_posts.md
│ ├── i18n
│ │ └── en.i18n.json
│ ├── lib
│ │ ├── getting_started.js
│ │ └── server
│ │ │ └── dummy_content.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-i18n
│ ├── .gitignore
│ ├── i18n.js
│ ├── package.js
│ └── versions.json
├── telescope-invites
│ ├── .gitignore
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ └── templates
│ │ │ │ ├── user_invites.html
│ │ │ │ └── user_invites.js
│ │ ├── invites.js
│ │ └── server
│ │ │ ├── invites.js
│ │ │ └── publications.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-kadira
│ ├── .gitignore
│ ├── lib
│ │ ├── kadira-settings.js
│ │ └── server
│ │ │ └── kadira.js
│ ├── package.js
│ └── versions.json
├── telescope-lib
│ ├── .gitignore
│ ├── lib
│ │ ├── autolink.js
│ │ ├── client
│ │ │ └── jquery.exists.js
│ │ ├── deep.js
│ │ ├── deep_extend.js
│ │ ├── lib.js
│ │ └── permissions.js
│ ├── package.js
│ └── versions.json
├── telescope-module-share
│ ├── .gitignore
│ ├── lib
│ │ ├── client
│ │ │ ├── post_share.html
│ │ │ ├── post_share.js
│ │ │ └── post_share.scss
│ │ └── share.js
│ ├── package.js
│ └── versions.json
├── telescope-newsletter
│ ├── .gitignore
│ ├── .npm
│ │ └── package
│ │ │ ├── .gitignore
│ │ │ ├── README
│ │ │ └── npm-shrinkwrap.json
│ ├── History.md
│ ├── README.md
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── stylesheets
│ │ │ │ └── newsletter_banner.scss
│ │ │ └── templates
│ │ │ │ ├── newsletter_banner.html
│ │ │ │ └── newsletter_banner.js
│ │ ├── newsletter.js
│ │ └── server
│ │ │ ├── campaign.js
│ │ │ ├── cron.js
│ │ │ ├── mailchimp.js
│ │ │ ├── routes.js
│ │ │ └── templates
│ │ │ ├── emailDigest.handlebars
│ │ │ ├── emailDigestConfirmation.handlebars
│ │ │ └── emailPostItem.handlebars
│ ├── package-tap.i18n
│ └── package.js
├── telescope-notifications
│ ├── .gitignore
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ └── templates
│ │ │ │ ├── notification_item.html
│ │ │ │ ├── notification_item.js
│ │ │ │ ├── notification_new_comment.html
│ │ │ │ ├── notification_new_reply.html
│ │ │ │ ├── notification_post_approved.html
│ │ │ │ ├── notifications_menu.html
│ │ │ │ ├── notifications_menu.js
│ │ │ │ ├── unsubscribe.html
│ │ │ │ └── unsubscribe.js
│ │ ├── herald.js
│ │ ├── notifications.js
│ │ └── server
│ │ │ ├── notifications-server.js
│ │ │ └── routes.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-post-by-feed
│ ├── .gitignore
│ ├── .npm
│ │ └── package
│ │ │ ├── .gitignore
│ │ │ ├── README
│ │ │ └── npm-shrinkwrap.json
│ ├── i18n
│ │ └── en.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── routes.js
│ │ │ ├── scss
│ │ │ │ └── feeds.scss
│ │ │ └── templates
│ │ │ │ ├── feed_item.html
│ │ │ │ ├── feed_item.js
│ │ │ │ ├── feeds.html
│ │ │ │ └── feeds.js
│ │ ├── feeds.js
│ │ └── server
│ │ │ ├── cron.js
│ │ │ ├── fetch_feeds.js
│ │ │ └── publications.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-releases
│ ├── .gitignore
│ ├── i18n
│ │ └── en.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── scss
│ │ │ │ └── releases.scss
│ │ │ └── templates
│ │ │ │ ├── current_release.html
│ │ │ │ └── current_release.js
│ │ ├── releases.js
│ │ └── server
│ │ │ ├── import_releases.js
│ │ │ └── publications.js
│ ├── package-tap.i18n
│ ├── package.js
│ ├── releases
│ │ ├── 0.11.0.md
│ │ ├── 0.11.1.md
│ │ ├── 0.12.0.md
│ │ ├── 0.13.0.md
│ │ └── 0.14.0.md
│ └── versions.json
├── telescope-rss
│ ├── .gitignore
│ ├── .npm
│ │ └── package
│ │ │ ├── .gitignore
│ │ │ ├── README
│ │ │ └── npm-shrinkwrap.json
│ ├── lib
│ │ └── server
│ │ │ ├── routes.js
│ │ │ └── rss.js
│ ├── package.js
│ └── versions.json
├── telescope-search
│ ├── .gitignore
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ ├── tr.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── css
│ │ │ │ └── search.css
│ │ │ ├── routes.js
│ │ │ └── views
│ │ │ │ ├── search.html
│ │ │ │ ├── search.js
│ │ │ │ ├── search_logs.html
│ │ │ │ └── search_logs.js
│ │ ├── search.js
│ │ └── server
│ │ │ ├── log_search.js
│ │ │ └── publications.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-singleday
│ ├── .gitignore
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ ├── tr.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ └── templates
│ │ │ │ ├── single_day.html
│ │ │ │ ├── single_day.js
│ │ │ │ ├── single_day_nav.html
│ │ │ │ └── single_day_nav.js
│ │ ├── routes.js
│ │ └── singleday.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-subscribe-to-posts
│ ├── .gitignore
│ ├── i18n
│ │ └── en.i18n.json
│ ├── lib
│ │ ├── client
│ │ │ ├── stylesheets
│ │ │ │ └── subscribe-to-posts.scss
│ │ │ └── templates
│ │ │ │ ├── post_subscribe.html
│ │ │ │ ├── post_subscribe.js
│ │ │ │ ├── user_subscribed_posts.html
│ │ │ │ └── user_subscribed_posts.js
│ │ ├── server
│ │ │ └── publications.js
│ │ └── subscribe-to-posts.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-tags
│ ├── .gitignore
│ ├── i18n
│ │ ├── de.i18n.json
│ │ ├── en.i18n.json
│ │ ├── es.i18n.json
│ │ ├── fr.i18n.json
│ │ ├── it.i18n.json
│ │ └── zh-CN.i18n.json
│ ├── lib
│ │ ├── categories.js
│ │ ├── client
│ │ │ ├── routes.js
│ │ │ ├── scss
│ │ │ │ └── categories.scss
│ │ │ └── templates
│ │ │ │ ├── categories.html
│ │ │ │ ├── categories.js
│ │ │ │ ├── categories_menu.html
│ │ │ │ ├── categories_menu.js
│ │ │ │ ├── category_item.html
│ │ │ │ ├── category_item.js
│ │ │ │ ├── post_categories.html
│ │ │ │ └── post_categories.js
│ │ ├── custom_fields.js
│ │ ├── hooks.js
│ │ └── server
│ │ │ └── publications.js
│ ├── package-tap.i18n
│ ├── package.js
│ └── versions.json
├── telescope-theme-base
│ ├── .gitignore
│ ├── lib
│ │ └── client
│ │ │ └── scss
│ │ │ ├── global
│ │ │ ├── _forms.scss
│ │ │ ├── _links.scss
│ │ │ ├── _main.scss
│ │ │ ├── _markdown.scss
│ │ │ ├── _tables.scss
│ │ │ └── _typography.scss
│ │ │ ├── includes
│ │ │ ├── _breakpoints.scss
│ │ │ ├── _colors.scss
│ │ │ └── _mixins.scss
│ │ │ ├── screen.scss
│ │ │ └── specific
│ │ │ ├── _avatars.scss
│ │ │ ├── _dropdown.scss
│ │ │ ├── _errors.scss
│ │ │ ├── _header.scss
│ │ │ ├── _layout.scss
│ │ │ ├── _loading.scss
│ │ │ ├── _mobile_nav.scss
│ │ │ ├── _notifications.scss
│ │ │ ├── _posts.scss
│ │ │ └── _users.scss
│ ├── package.js
│ └── versions.json
├── telescope-theme-hubble
│ ├── .gitignore
│ ├── lib
│ │ ├── client
│ │ │ └── scss
│ │ │ │ ├── modules
│ │ │ │ ├── _accounts.scss
│ │ │ │ ├── _banners.scss
│ │ │ │ ├── _comments.scss
│ │ │ │ ├── _dialogs.scss
│ │ │ │ ├── _errors.scss
│ │ │ │ ├── _icons.scss
│ │ │ │ ├── _nav.scss
│ │ │ │ ├── _posts.scss
│ │ │ │ └── _user-profile.scss
│ │ │ │ ├── partials
│ │ │ │ ├── _colors.scss
│ │ │ │ ├── _grid.scss
│ │ │ │ ├── _icons.scss
│ │ │ │ ├── _mixins.scss
│ │ │ │ ├── _tooltips.scss
│ │ │ │ └── _typography.scss
│ │ │ │ └── screen.scss
│ │ └── hubble.js
│ ├── package.js
│ └── versions.json
└── telescope-update-prompt
│ ├── .gitignore
│ ├── lib
│ ├── client
│ │ ├── templates
│ │ │ ├── update_banner.css
│ │ │ ├── update_banner.html
│ │ │ └── update_banner.js
│ │ └── update.js
│ └── server
│ │ └── phone_home.js
│ ├── package.js
│ └── versions.json
├── project-tap.i18n
├── public
└── img
│ ├── bg-black.png
│ ├── bg-black@2x.png
│ ├── bg-header.png
│ ├── bg-header@2x.png
│ ├── bg.png
│ ├── bg@2x.png
│ ├── default-avatar.png
│ ├── favicon.ico
│ ├── loading-balls.svg
│ ├── loading.gif
│ ├── loading.svg
│ ├── logo.png
│ ├── logo@2x.png
│ ├── telescope-logo.png
│ ├── telescope-logo2.png
│ ├── telescope-logo@2x.png
│ └── thegrid.svg
├── sandstorm-pkgdef.capnp
├── scss.json
├── server
├── migrations.js
├── publications
│ ├── posts_list.js
│ ├── settings.js
│ ├── single_comment.js
│ ├── single_post.js
│ ├── user_profile.js
│ ├── users.js
│ └── users_dashboard.js
├── scoring.js
├── start.js
├── start_cron.js
├── testing.js
└── users.js
├── testing.settings.json
└── tests
└── jasmine
├── client
└── unit
│ ├── commentItemSpec.js
│ └── navSpec.js
└── server
└── integration
└── packages
└── telescope-lib
└── permissionsSpec.js
/.editorconfig:
--------------------------------------------------------------------------------
1 | # editorconfig.org
2 |
3 | root = true
4 |
5 | [*.{js,html}]
6 |
7 | charset = utf-8
8 | end_of_line = lf
9 | indent_brace_style = 1TBS
10 | indent_size = 2
11 | indent_style = space
12 | insert_final_newline = true
13 | max_line_length = 80
14 | quote_type = auto
15 | spaces_around_operators = true
16 | trim_trailing_whitespace = true
17 |
18 | [*.md]
19 |
20 | trim_trailing_whitespace = false
21 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | npm-debug.log
2 | *.scssc
3 | .sass-cache/*
4 | .DS_Store
5 | *-ck.js
6 | providers_secret.js
7 | *.sublime-project
8 |
9 | *.sublime-workspace
10 | codekit-config.json
11 |
12 | config.rb
13 |
14 | deploy.sh
15 |
16 | .demeteorized
17 |
18 | dump/
19 | dump/*
20 |
21 | settings.json
22 | settings.json.not-used
23 | .idea
24 |
25 | scratch
26 |
27 | .deploy
28 | .deploy/*
29 | ### Meteor template
30 | .meteor/local
31 | .meteor/meteorite
32 | mup.json
33 | .meteor-spk
34 |
--------------------------------------------------------------------------------
/.meteor/.finished-upgraders:
--------------------------------------------------------------------------------
1 | # This file contains information which helps Meteor properly upgrade your
2 | # app when you run 'meteor update'. You should check it into version control
3 | # with your project.
4 |
5 | notices-for-0.9.0
6 | notices-for-0.9.1
7 | 0.9.4-platform-file
8 |
--------------------------------------------------------------------------------
/.meteor/.gitignore:
--------------------------------------------------------------------------------
1 | local
2 | meteorite
3 |
--------------------------------------------------------------------------------
/.meteor/.id:
--------------------------------------------------------------------------------
1 | # This file contains a token that is unique to your project.
2 | # Check it into your repository along with the rest of this directory.
3 | # It can be used for purposes such as:
4 | # - ensuring you don't accidentally deploy one app on top of another
5 | # - providing package authors with aggregated statistics
6 |
7 | 4ibiemui4bqn1j744h7
8 |
--------------------------------------------------------------------------------
/.meteor/cordova-plugins:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/.meteor/platforms:
--------------------------------------------------------------------------------
1 | server
2 | browser
3 |
--------------------------------------------------------------------------------
/.meteor/release:
--------------------------------------------------------------------------------
1 | METEOR@1.0.2.1
2 |
--------------------------------------------------------------------------------
/.travis.yml:
--------------------------------------------------------------------------------
1 | language: node_js
2 | node_js:
3 | - "0.10"
4 | before_install:
5 | - curl https://install.meteor.com | /bin/sh
6 |
7 | before_script:
8 | - export DISPLAY=:99.0
9 | - sh -e /etc/init.d/xvfb start
10 | # Add testing package since it's not currently enabled in Telescope
11 | - printf "sanjo:jasmine@0.11.0" >> .meteor/packages
12 |
13 | script:
14 | - JASMINE_BROWSER=Firefox meteor --test
--------------------------------------------------------------------------------
/README.nitrous.md:
--------------------------------------------------------------------------------
1 | # Setup for Nitrous.IO
2 |
3 | Before you can run this project, you will need to install Meteor with Autoparts (open-source package manager built specifically for Nitrous.IO boxes).
4 |
5 | Run the following commands in the Terminal below:
6 |
7 | 1. `cd ~/workspace/Telescope/`
8 | 2. `parts install meteor`
9 | 3. `meteor -p 0.0.0.0:3000`
10 |
11 | Usually you would just run `meteor`, but for nitrous environment host `0.0.0.0` is required.
12 |
13 | To preview the app, go to the "Preview Menu" and click "Port 3000"
14 |
--------------------------------------------------------------------------------
/app-graphics/telescope-128.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/app-graphics/telescope-128.png
--------------------------------------------------------------------------------
/app-graphics/telescope-150.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/app-graphics/telescope-150.png
--------------------------------------------------------------------------------
/app-graphics/telescope-24.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/app-graphics/telescope-24.png
--------------------------------------------------------------------------------
/app-graphics/telescope-256.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/app-graphics/telescope-256.png
--------------------------------------------------------------------------------
/app-graphics/telescope-300.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/app-graphics/telescope-300.png
--------------------------------------------------------------------------------
/app-graphics/telescope-48.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/app-graphics/telescope-48.png
--------------------------------------------------------------------------------
/client/main.html:
--------------------------------------------------------------------------------
1 |
2 | Loading...
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/client/main.js:
--------------------------------------------------------------------------------
1 | // Session variables
2 | Session.set('postsLimit', getSetting('postsPerPage', 10));
3 |
4 | // Sort postModules array position using modulePositions as index
5 | postModules = _.sortBy(postModules, 'order');
6 |
7 | postHeading = _.sortBy(postHeading, 'order');
8 |
9 | postMeta = _.sortBy(postMeta, 'order');
10 |
11 | Meteor.startup(function () {
12 | $('#rss-link').attr('title', i18n.t('new_posts'));
13 | });
14 |
15 | // AutoForm.debug();
--------------------------------------------------------------------------------
/client/views/admin/settings_form.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{#if this.hasSettings}}
4 | {{> quickForm collection="Settings" id="updateSettingsForm" type="update" doc=this.settings label-class="control-label" input-col-class="controls" template="telescope"}}
5 | {{else}}
6 | {{> quickForm collection="Settings" id="insertSettingsForm" type="insert" template="telescope" label-class="control-label" input-col-class="controls"}}
7 | {{/if}}
8 |
9 |
--------------------------------------------------------------------------------
/client/views/admin/settings_form.js:
--------------------------------------------------------------------------------
1 | AutoForm.hooks({
2 | updateSettingsForm: {
3 |
4 | before: {
5 | update: function(docId, modifier, template) {
6 | template.$('button[type=submit]').addClass('loading');
7 | return modifier;
8 | }
9 | },
10 |
11 | onSuccess: function(operation, result, template) {
12 | template.$('button[type=submit]').removeClass('loading');
13 | },
14 |
15 | onError: function(operation, result, template) {
16 | template.$('button[type=submit]').removeClass('loading');
17 | }
18 |
19 | },
20 | insertSettingsForm: {
21 |
22 | before: {
23 | insert: function(doc, template) {
24 | template.$('button[type=submit]').addClass('loading');
25 | return doc;
26 | }
27 | },
28 |
29 | onSuccess: function(operation, result, template) {
30 | template.$('button[type=submit]').removeClass('loading');
31 | },
32 |
33 | onError: function(operation, result, template) {
34 | template.$('button[type=submit]').removeClass('loading');
35 | }
36 |
37 | }
38 | });
--------------------------------------------------------------------------------
/client/views/comments/comment_deleted.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "your_comment_has_been_deleted"}}
4 |
5 |
--------------------------------------------------------------------------------
/client/views/comments/comment_edit.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{#with comment}}
4 |
14 | {{/with}}
15 |
16 |
--------------------------------------------------------------------------------
/client/views/comments/comment_edit.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('comment_edit')].events({
2 | 'click input[type=submit]': function(e, instance){
3 | var comment = this;
4 | var content = instance.$('#body').val();
5 |
6 | e.preventDefault();
7 |
8 | if(!Meteor.user())
9 | throw i18n.t('you_must_be_logged_in');
10 |
11 | Comments.update(comment._id, {
12 | $set: {
13 | body: content
14 | }
15 | });
16 |
17 | trackEvent("edit comment", {'postId': comment.postId, 'commentId': comment._id});
18 | Router.go('post_page_comment', {_id: comment.postId, commentId: comment._id});
19 | },
20 | 'click .delete-link': function(e){
21 | var comment = this;
22 |
23 | e.preventDefault();
24 |
25 | if(confirm(i18n.t("are_you_sure"))){
26 | Meteor.call('removeComment', comment._id);
27 | Router.go('post_page', {_id: comment.postId});
28 | flashMessage("Your comment has been deleted.", "success");
29 | }
30 | }
31 | });
32 |
--------------------------------------------------------------------------------
/client/views/comments/comment_form.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if canComment}}
3 |
13 | {{else}}
14 | {{reason}}
15 | {{/if}}
16 |
17 |
--------------------------------------------------------------------------------
/client/views/comments/comment_list.html:
--------------------------------------------------------------------------------
1 |
2 |
7 | {{#each threadModules}}
8 | {{> UI.dynamic template=getTemplate data=..}}
9 | {{/each}}
10 |
11 |
--------------------------------------------------------------------------------
/client/views/comments/comment_list.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('comment_list')].helpers({
2 | comment_item: function () {
3 | return getTemplate('comment_item');
4 | },
5 | child_comments: function(){
6 | var post = this;
7 | var comments = Comments.find({postId: post._id, parentCommentId: null}, {sort: {score: -1, postedAt: -1}});
8 | return comments;
9 | },
10 | threadModules: function () {
11 | return threadModules;
12 | },
13 | getTemplate: function () {
14 | return getTemplate(this.template);
15 | }
16 | });
17 |
18 | Template[getTemplate('comment_list')].rendered = function(){
19 | // once all comments have been rendered, activate comment queuing for future real-time comments
20 | window.queueComments = true;
21 | };
--------------------------------------------------------------------------------
/client/views/comments/comment_reply.html:
--------------------------------------------------------------------------------
1 |
2 |
21 |
22 |
--------------------------------------------------------------------------------
/client/views/comments/comment_reply.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('comment_reply')].helpers({
2 | post_item: function () {
3 | return getTemplate('post_item');
4 | },
5 | comment_item: function () {
6 | return getTemplate('comment_item');
7 | },
8 | comment_form: function () {
9 | return getTemplate('comment_form');
10 | },
11 | post: function () {
12 | if(this.comment){ // XXX
13 | var post = Posts.findOne(this.comment.postId);
14 | return post;
15 | }
16 | }
17 | });
--------------------------------------------------------------------------------
/client/views/common/css.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('css')].helpers({
2 | });
--------------------------------------------------------------------------------
/client/views/common/footer.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if footerCode}}
3 |
6 | {{/if}}
7 | {{#each footerModules}}
8 | {{> UI.dynamic template=getTemplate}}
9 | {{/each}}
10 |
--------------------------------------------------------------------------------
/client/views/common/footer.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('footer')].helpers({
2 | footerCode: function(){
3 | return getSetting('footerCode');
4 | },
5 | footerClass: function(){
6 | return Session.get('isPostsList') ? 'absolute' : 'static';
7 | },
8 | footerModules: function () {
9 | return footerModules;
10 | },
11 | getTemplate: function () {
12 | return getTemplate(this.template);
13 | }
14 | });
--------------------------------------------------------------------------------
/client/views/common/layout.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{> UI.dynamic template=css}}
4 |
5 | {{> UI.dynamic template=mobile_nav}}
6 |
7 | {{> UI.dynamic template=nav}}
8 |
9 | {{> UI.dynamic template=messages}}
10 | {{#each heroModules}}
11 | {{> UI.dynamic template=getTemplate}}
12 | {{/each}}
13 | {{> yield}}
14 | {{> UI.dynamic template=footer}}
15 |
16 |
17 |
18 | {{{extraCode}}}
19 |
20 |
--------------------------------------------------------------------------------
/client/views/common/layout.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('layout')].helpers({
2 | mobile_nav: function () {
3 | return getTemplate('mobile_nav');
4 | },
5 | nav: function () {
6 | return getTemplate('nav');
7 | },
8 | messages: function () {
9 | return getTemplate('messages');
10 | },
11 | notifications: function () {
12 | return getTemplate('notifications');
13 | },
14 | footer: function () {
15 | return getTemplate('footer');
16 | },
17 | pageName : function(){
18 | return getCurrentTemplate();
19 | },
20 | css: function () {
21 | return getTemplate('css');
22 | },
23 | heroModules: function () {
24 | return heroModules;
25 | },
26 | getTemplate: function () {
27 | return getTemplate(this.template);
28 | }
29 | });
30 |
31 | Template[getTemplate('layout')].created = function(){
32 | Session.set('currentScroll', null);
33 | };
34 |
35 | Template[getTemplate('layout')].rendered = function(){
36 | if(currentScroll=Session.get('currentScroll')){
37 | $('body').scrollTop(currentScroll);
38 | Session.set('currentScroll', null);
39 | }
40 | };
41 |
--------------------------------------------------------------------------------
/client/views/common/message_item.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if show}}
3 |
4 |
5 | {{message}}
6 |
7 |
8 | {{/if}}
9 |
--------------------------------------------------------------------------------
/client/views/common/message_item.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('message_item')].helpers({
2 |
3 | });
4 |
5 | Template[getTemplate('message_item')].created = function(){
6 | var messageId=this.data._id;
7 | Meteor.setTimeout(function(){
8 | Messages.update(messageId, {$set: {seen:true}});
9 | }, 100);
10 | };
--------------------------------------------------------------------------------
/client/views/common/messages.html:
--------------------------------------------------------------------------------
1 |
2 | {{#each messages}}
3 | {{> UI.dynamic template=message_item}}
4 | {{/each}}
5 |
--------------------------------------------------------------------------------
/client/views/common/messages.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('messages')].helpers({
2 | message_item: function () {
3 | return getTemplate('message_item');
4 | },
5 | messages: function(){
6 | return Messages.find({show: true});
7 | }
8 | });
--------------------------------------------------------------------------------
/client/views/errors/already_logged_in.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "you_are_already_logged_in"}}
4 |
5 |
--------------------------------------------------------------------------------
/client/views/errors/loading.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{>spinner}}
4 |
5 |
--------------------------------------------------------------------------------
/client/views/errors/loading.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('loading')].helpers({
2 | log: function () {
3 | console.log('loading…')
4 | }
5 | });
--------------------------------------------------------------------------------
/client/views/errors/no_account.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "sorry_this_is_a_private_site_please_sign_up_first"}}
4 | {{landingPageText}}
5 |
8 |
9 |
--------------------------------------------------------------------------------
/client/views/errors/no_account.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('no_account')].helpers({
2 | landingPageText: function(){
3 | return getSetting("landingPageText");
4 | }
5 | });
6 | Template[getTemplate('no_account')].events({
7 | 'click .twitter-button': function(){
8 | Meteor.loginWithTwitter(function(){
9 | Router.go('/');
10 | });
11 | }
12 | });
--------------------------------------------------------------------------------
/client/views/errors/no_invite.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "thanks_for_signing_up"}}
4 | {{afterSignupText}}
5 |
{{_ "the_site_is_currently_invite_only_but_we_will_let_you_know_as_soon_as_a_spot_opens_up"}}
6 |
7 |
--------------------------------------------------------------------------------
/client/views/errors/no_invite.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('no_invite')].helpers({
2 | afterSignupText: function(){
3 | return getSetting("afterSignupText");
4 | }
5 | });
--------------------------------------------------------------------------------
/client/views/errors/no_rights.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{_ "sorry_you_dont_have_the_rights_to_view_this_page"}}
4 |
5 |
--------------------------------------------------------------------------------
/client/views/errors/not_found.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "not_found"}}
4 |
{{_ "were_sorry_whatever_you_were_looking_for_isnt_here"}}
5 |
6 |
--------------------------------------------------------------------------------
/client/views/forms/urlCustomType.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/client/views/forms/urlCustomType.js:
--------------------------------------------------------------------------------
1 | AutoForm.addInputType("bootstrap-url", {
2 | template: "afBootstrapUrl",
3 | valueOut: function () {
4 | var url = this.val();
5 | if(!!url)
6 | return (url.substring(0, 7) == "http://" || url.substring(0, 8) == "https://") ? url : "http://"+url;
7 | }
8 | });
9 |
10 | Template.afBootstrapUrl_bootstrap3.helpers({
11 | atts: function addFormControlAtts() {
12 | console.log(this)
13 | var atts = _.clone(this.atts);
14 | // Add bootstrap class
15 | atts = AutoForm.Utility.addClass(atts, "form-control");
16 | return atts;
17 | }
18 | });
19 |
20 |
--------------------------------------------------------------------------------
/client/views/nav/admin_menu.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if isAdmin}}
3 |
13 | {{/if}}
14 |
--------------------------------------------------------------------------------
/client/views/nav/admin_menu.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('adminMenu')].helpers({
2 | menuItem: function () {
3 | return getTemplate('menuItem');
4 | },
5 | menu: function () {
6 | return adminMenu;
7 | }
8 | });
--------------------------------------------------------------------------------
/client/views/nav/menu_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | {{#if description}}{{/if}}
6 |
7 |
8 |
--------------------------------------------------------------------------------
/client/views/nav/mobile_nav.html:
--------------------------------------------------------------------------------
1 |
2 |
19 |
--------------------------------------------------------------------------------
/client/views/nav/mobile_nav.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('mobile_nav')].helpers({
2 | primaryNav: function () {
3 | return primaryNav;
4 | },
5 | secondaryNav: function () {
6 | return secondaryNav;
7 | },
8 | getTemplate: function () {
9 | return getTemplate(this).template;
10 | }
11 | });
12 |
13 | Template[getTemplate('mobile_nav')].events({
14 | 'click .dropdown-sub-level': function () {
15 | $('body').toggleClass('mobile-nav-open');
16 | }
17 | });
18 |
19 | Template[getTemplate('mobile_nav')].events({
20 | 'click .dropdown-top-level': function (e) {
21 | e.preventDefault();
22 | $(e.currentTarget).next().slideToggle('fast');
23 | },
24 | 'click .mobile-nav a': function (e) {
25 | if (e.target.className.indexOf('dropdown-top-level') == -1){
26 | $('body').removeClass('mobile-nav-open');
27 | }
28 | }
29 | });
--------------------------------------------------------------------------------
/client/views/nav/nav.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('nav')].helpers({
2 | primaryNav: function () {
3 | return _.sortBy(primaryNav, 'order');
4 | },
5 | hasPrimaryNav: function () {
6 | return !!primaryNav.length;
7 | },
8 | secondaryNav: function () {
9 | return _.sortBy(secondaryNav, 'order');
10 | },
11 | hasSecondaryNav: function () {
12 | return !!secondaryNav.length;
13 | },
14 | dropdownClass: function () {
15 | return getThemeSetting('useDropdowns', true) ? 'has-dropdown' : 'no-dropdown';
16 | },
17 | getTemplate: function () {
18 | return getTemplate(this.template);
19 | },
20 | site_title: function(){
21 | return getSetting('title', "Telescope");
22 | },
23 | logo_url: function(){
24 | return getSetting('logoUrl');
25 | }
26 | });
27 |
28 | Template[getTemplate('nav')].events({
29 | 'click .mobile-menu-button': function(e){
30 | e.preventDefault();
31 | $('body').toggleClass('mobile-nav-open');
32 | }
33 | });
--------------------------------------------------------------------------------
/client/views/nav/submit_button.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if canPost}}
3 |
4 | {{/if}}
5 |
--------------------------------------------------------------------------------
/client/views/nav/user_menu.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if isLoggedIn}}
3 |
12 | {{else}}
13 | Not Signed In
14 | {{/if}}
15 |
16 |
--------------------------------------------------------------------------------
/client/views/nav/user_menu.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('userMenu')].helpers({
2 | isLoggedIn: function () {
3 | return !!Meteor.user();
4 | },
5 | name: function () {
6 | return getDisplayName(Meteor.user());
7 | },
8 | profileUrl: function () {
9 | return Router.path('user_profile', {_idOrSlug: Meteor.user().slug});
10 | },
11 | userEditUrl: function () {
12 | return Router.path('user_edit', {slug: Meteor.user().slug});
13 | }
14 | });
15 |
--------------------------------------------------------------------------------
/client/views/nav/views_menu.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if canView}}
3 |
13 | {{/if}}
14 |
--------------------------------------------------------------------------------
/client/views/nav/views_menu.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('viewsMenu')].helpers({
2 | menuItem: function () {
3 | return getTemplate('menuItem');
4 | },
5 | views: function () {
6 | return viewsMenu;
7 | }
8 | });
9 |
--------------------------------------------------------------------------------
/client/views/posts/after_post_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/client/views/posts/before_post_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_actions.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | …
4 |
5 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_actions.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postActions')].helpers({
2 |
3 | });
4 |
5 | Template[getTemplate('postActions')].events({
6 | 'click .toggle-actions-link': function(e, instance){
7 | e.preventDefault();
8 | var $post = $(e.target).parents('.post');
9 | var h = $post.height();
10 | if ($post.hasClass('show-actions')) {
11 | $post.height('auto');
12 | $post.removeClass('show-actions');
13 | } else {
14 | $post.height(h+'px');
15 | $post.addClass('show-actions');
16 | }
17 | }
18 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_admin.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if isAdmin}}
3 |
4 | {{#if postsMustBeApproved}}
5 | |
6 | {{#if isApproved}}
7 |
{{_ "unapprove"}}
8 | {{else}}
9 |
{{_ "approve"}}
10 | {{/if}}
11 | {{/if}}
12 | | {{_ "score"}}: {{shortScore}}, {{_ "clicks"}}: {{clickCount}}, {{_ "views"}}: {{viewCount}}
13 |
14 | {{/if}}
15 |
16 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_admin.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postAdmin')].helpers({
2 | postsMustBeApproved: function () {
3 | return !!getSetting('requirePostsApproval');
4 | },
5 | isApproved: function(){
6 | return this.status == STATUS_APPROVED;
7 | },
8 | shortScore: function(){
9 | return Math.floor(this.score*1000)/1000;
10 | }
11 | });
12 |
13 | Template[getTemplate('postAdmin')].events({
14 | 'click .approve-link': function(e, instance){
15 | Meteor.call('approvePost', this);
16 | e.preventDefault();
17 | },
18 | 'click .unapprove-link': function(e, instance){
19 | Meteor.call('unapprovePost', this);
20 | e.preventDefault();
21 | }
22 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_author.html:
--------------------------------------------------------------------------------
1 |
2 | {{userName userId}}
3 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_avatars.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{> avatar userId=userId shape="circle"}}
4 |
5 | {{#if commenters}}
6 |
13 | {{/if}}
14 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_avatars.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postAvatars')].helpers({
2 | commenters: function () {
3 | // remove post author ID from commenters to avoid showing author's avatar again
4 | // limit to 4 commenters in case there's more
5 | // TODO: show a "..." sign or something
6 | return _.first(_.without(this.commenters, this.userId), 4);
7 | }
8 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_comments_link.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
7 |
8 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_content.html:
--------------------------------------------------------------------------------
1 |
2 | {{#each postThumbnail}}
3 | {{> UI.dynamic template=getTemplate data=..}}
4 | {{/each}}
5 |
6 |
7 | {{#each postHeading}}
8 | {{> UI.dynamic template=getTemplate data=..}}
9 | {{/each}}
10 |
11 |
12 | {{#each postMeta}}
13 | {{> UI.dynamic template=getTemplate data=..}}
14 | {{/each}}
15 |
16 |
17 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_content.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postContent')].helpers({
2 | postThumbnail: function () {
3 | return postThumbnail;
4 | },
5 | postHeading: function () {
6 | return postHeading;
7 | },
8 | postMeta: function () {
9 | return postMeta;
10 | },
11 | getTemplate: function () {
12 | return getTemplate(this.template);
13 | },
14 | sourceLink: function(){
15 | return !!this.url ? this.url : "/posts/"+this._id;
16 | },
17 | current_domain: function(){
18 | return "http://"+document.domain;
19 | },
20 | timestamp: function(){
21 | time = this.status == STATUS_APPROVED ? this.postedAt : this.createdAt;
22 | return moment(time).format("MMMM Do, h:mm:ss a");
23 | },
24 | userAvatar: function(){
25 | // THIS FUNCTION IS DEPRECATED -- package bengott:avatar is used instead.
26 | var author = Meteor.users.findOne(this.userId, {reactive: false});
27 | if(!!author)
28 | return getAvatarUrl(author); // ALSO DEPRECATED
29 | },
30 | inactiveClass: function(){
31 | return (isAdmin(Meteor.user()) && this.inactive) ? i18n.t('inactive') : "";
32 | },
33 | commentsDisplayText: function(){
34 | return this.comments == 1 ? i18n.t('comment') : i18n.t('comments');
35 | }
36 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_discuss.html:
--------------------------------------------------------------------------------
1 |
2 |
6 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_domain.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if url}}{{domain}} {{/if}}
3 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_domain.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postDomain')].helpers({
2 | domain: function(){
3 | var a = document.createElement('a');
4 | a.href = this.url;
5 | return a.hostname;
6 | }
7 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_info.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{baseScore}}
4 |
{{pointsUnitDisplayText}}
5 | {{#if postedAt}}
{{timeAgo postedAt}} {{/if}}
6 | {{#if canEdit this}}
7 | |
{{_ "edit"}}
8 | {{/if}}
9 |
10 |
11 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_info.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postInfo')].helpers({
2 | pointsUnitDisplayText: function(){
3 | return this.upvotes == 1 ? i18n.t('point') : i18n.t('points');
4 | },
5 | getTemplate: function() {
6 | return getTemplate("postAuthor");
7 | }
8 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_rank.html:
--------------------------------------------------------------------------------
1 |
2 | {{oneBasedRank}}
3 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_rank.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postRank')].helpers({
2 | oneBasedRank: function(){
3 | if (typeof this.rank !== 'undefined') {
4 | return this.rank + 1;
5 | }
6 | }
7 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_title.html:
--------------------------------------------------------------------------------
1 |
2 | {{title}}
3 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_title.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postTitle')].helpers({
2 | postLink: function(){
3 | return !!this.url ? getOutgoingUrl(this.url) : "/posts/"+this._id;
4 | },
5 | postTarget: function() {
6 | return !!this.url ? '_blank' : '';
7 | }
8 | });
--------------------------------------------------------------------------------
/client/views/posts/modules/post_upvote.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if upvoted}}
3 |
4 |
5 |
6 | {{else}}
7 |
8 |
9 |
10 | {{/if}}
11 |
--------------------------------------------------------------------------------
/client/views/posts/modules/post_upvote.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postUpvote')].helpers({
2 | upvoted: function(){
3 | var user = Meteor.user();
4 | if(!user) return false;
5 | return _.include(this.upvoters, user._id);
6 | }
7 | });
8 |
9 | Template[getTemplate('postUpvote')].events({
10 | 'click .upvote-link': function(e, instance){
11 | var post = this;
12 | e.preventDefault();
13 | if(!Meteor.user()){
14 | Router.go('atSignIn');
15 | flashMessage(i18n.t("please_log_in_first"), "info");
16 | }
17 | Meteor.call('upvotePost', post, function(error, result){
18 | trackEvent("post upvoted", {'_id': post._id});
19 | });
20 | }
21 | });
22 |
--------------------------------------------------------------------------------
/client/views/posts/post_body.html:
--------------------------------------------------------------------------------
1 |
2 | {{{htmlBody}}}
3 |
--------------------------------------------------------------------------------
/client/views/posts/post_edit.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | {{> quickForm collection="Posts" doc=post id="editPostForm" template="telescope" label-class="control-label" input-col-class="controls" type="method" meteormethod="editPost"}}
5 |
6 |
7 |
10 |
11 |
--------------------------------------------------------------------------------
/client/views/posts/post_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{#each postModules}}
4 |
5 | {{> UI.dynamic template=getTemplate data=..}}
6 |
7 | {{/each}}
8 |
9 |
10 |
--------------------------------------------------------------------------------
/client/views/posts/post_item.js:
--------------------------------------------------------------------------------
1 | var post = {};
2 |
3 | Template[getTemplate('post_item')].created = function () {
4 | post = this.data;
5 | };
6 |
7 | Template[getTemplate('post_item')].helpers({
8 | postModules: function () {
9 | return postModules;
10 | },
11 | getTemplate: function () {
12 | return getTemplate(this.template);
13 | },
14 | moduleContext: function () { // not used for now
15 | var module = this;
16 | module.templateClass = camelToDash(this.template) + ' ' + this.position + ' cell';
17 | module.post = post;
18 | return module;
19 | },
20 | moduleClass: function () {
21 | return camelToDash(this.template) + ' post-module';
22 | },
23 | postClass: function () {
24 | var post = this;
25 | var postAuthorClass = "author-"+post.author;
26 |
27 | var postClass = postClassCallbacks.reduce(function(result, currentFunction) {
28 | return currentFunction(post, result);
29 | }, postAuthorClass);
30 |
31 | return postClass;
32 | }
33 | });
34 |
--------------------------------------------------------------------------------
/client/views/posts/post_list/posts_list.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{> UI.dynamic template=postsListIncoming data=incoming}}
4 |
5 | {{#each postsCursor}}
6 | {{> UI.dynamic template=before_post_item}}
7 | {{> UI.dynamic template=post_item}}
8 | {{> UI.dynamic template=after_post_item}}
9 | {{/each}}
10 |
11 | {{> UI.dynamic template=postsLoadMore}}
12 |
13 |
--------------------------------------------------------------------------------
/client/views/posts/post_list/posts_list_incoming.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if count}}
3 |
4 |
5 | {{_ "view"}} {{count}} {{_ "new"}} {{pluralize count "post"}}
6 |
7 |
8 | {{/if}}
9 |
--------------------------------------------------------------------------------
/client/views/posts/post_list/posts_list_incoming.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postsListIncoming')].events({
2 | 'click .show-new': function(e, instance) {
3 | Session.set('listPopulatedAt', new Date());
4 | }
5 | });
--------------------------------------------------------------------------------
/client/views/posts/post_list/posts_load_more.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if postsReady}}
3 | {{#if hasPosts}}
4 | {{#if hasMorePosts}}
5 | {{_ "load_more"}}
6 | {{/if}}
7 | {{else}}
8 | {{_ "sorry_we_couldnt_find_any_posts"}}
9 | {{/if}}
10 | {{else}}
11 | {{> spinner}}
12 | {{/if}}
13 |
--------------------------------------------------------------------------------
/client/views/posts/post_list/posts_load_more.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postsLoadMore')].helpers({
2 | postsReady: function () {
3 | return this.postsReady;
4 | },
5 | hasPosts: function () {
6 | return !!this.postsCursor.count();
7 | }
8 | });
9 |
10 | Template[getTemplate('postsLoadMore')].events({
11 | 'click .more-button': function (event, instance) {
12 | event.preventDefault();
13 | if (this.controllerInstance) {
14 | // controller is a template
15 | this.loadMoreHandler(this.controllerInstance);
16 | } else {
17 | // controller is router
18 | this.loadMoreHandler();
19 | }
20 | }
21 | });
--------------------------------------------------------------------------------
/client/views/posts/post_page.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | {{> UI.dynamic template=post_item}}
5 |
6 | {{#if body}}
7 | {{> UI.dynamic template=post_body}}
8 | {{/if}}
9 | {{> UI.dynamic template=comment_form}}
10 | {{> UI.dynamic template=comment_list}}
11 |
12 |
13 |
--------------------------------------------------------------------------------
/client/views/posts/post_page.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('post_page')].helpers({
2 | post_item: function () {
3 | return getTemplate('post_item');
4 | },
5 | post_body: function () {
6 | return getTemplate('post_body');
7 | },
8 | comment_form: function () {
9 | return getTemplate('comment_form');
10 | },
11 | comment_list: function () {
12 | return getTemplate('comment_list');
13 | }
14 | });
15 |
16 | Template[getTemplate('post_page')].rendered = function(){
17 | $('body').scrollTop(0);
18 | };
19 |
--------------------------------------------------------------------------------
/client/views/posts/post_submit.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | {{> quickForm collection="Posts" id="submitPostForm" template="telescope" label-class="control-label" input-col-class="controls" type="method" meteormethod="submitPost"}}
5 |
6 |
7 |
--------------------------------------------------------------------------------
/client/views/users/profile/user_comments.html:
--------------------------------------------------------------------------------
1 |
2 |
28 |
--------------------------------------------------------------------------------
/client/views/users/profile/user_downvoted_posts.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "downvoted_posts"}}
4 |
5 |
6 |
7 | Post
8 | Downvoted At
9 |
10 |
11 | {{#each posts}}
12 |
13 | {{title}}
14 | {{formatDate votedAt "MM/DD/YYYY, HH:mm"}}
15 |
16 | {{/each}}
17 | {{#if hasMorePosts}}
18 |
19 |
20 | {{_ "load_more"}}
21 |
22 |
23 | {{/if}}
24 |
25 |
26 |
--------------------------------------------------------------------------------
/client/views/users/profile/user_info.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('userInfo')].helpers({
2 | canEditProfile: function() {
3 | var currentUser = Meteor.user();
4 | return currentUser && (this._id == currentUser._id || isAdmin(currentUser));
5 | },
6 | createdAtFormatted: function() {
7 | return this.createdAt;
8 | },
9 | canInvite: function() {
10 | // if the user is logged in, the target user hasn't been invited yet, invites are enabled, and user is not viewing their own profile
11 | return Meteor.user() && Meteor.user()._id != this._id && !isInvited(this) && invitesEnabled() && can.invite(Meteor.user());
12 | },
13 | inviteCount: function() {
14 | return Meteor.user().inviteCount;
15 | },
16 | getTwitterName: function () {
17 | return getTwitterName(this);
18 | },
19 | getGitHubName: function () {
20 | return getGitHubName(this);
21 | }
22 | });
23 |
24 | Template[getTemplate('userInfo')].events({
25 | 'click .invite-link': function(e, instance){
26 | Meteor.call('inviteUser', instance.data.user._id);
27 | flashMessage('Thanks, user has been invited.', "success");
28 | }
29 | });
30 |
--------------------------------------------------------------------------------
/client/views/users/profile/user_posts.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "posts"}}
4 |
5 |
6 |
7 | Post
8 | Created At
9 |
10 |
11 | {{#each posts}}
12 |
13 | {{title}}
14 | {{formatDate createdAt "MM/DD/YYYY, HH:mm"}}
15 |
16 | {{/each}}
17 | {{#if isReady}}
18 | {{#if hasMorePosts}}
19 |
20 |
21 | {{_ "load_more"}}
22 |
23 |
24 | {{/if}}
25 | {{else}}
26 |
27 |
28 |
29 | {{>spinner}}
30 |
31 |
32 |
33 | {{/if}}
34 |
35 |
36 |
--------------------------------------------------------------------------------
/client/views/users/profile/user_upvoted_posts.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "upvoted_posts"}}
4 |
5 |
6 |
7 | Post
8 | Upvoted At
9 |
10 |
11 | {{#each posts}}
12 |
13 | {{title}}
14 | {{formatDate votedAt "MM/DD/YYYY, HH:mm"}}
15 |
16 | {{/each}}
17 | {{#if hasMorePosts}}
18 |
19 |
20 | {{_ "load_more"}}
21 |
22 |
23 | {{/if}}
24 |
25 |
26 |
--------------------------------------------------------------------------------
/client/views/users/sandstorm_sign_in.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/client/views/users/sign_out.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "you_ve_been_signed_out"}}
4 |
5 |
--------------------------------------------------------------------------------
/client/views/users/user_edit.html:
--------------------------------------------------------------------------------
1 |
2 | {{#with user}}
3 | {{#each userProfileEdit}}
4 | {{> UI.dynamic template=getTemplate data=..}}
5 | {{/each}}
6 | {{/with}}
7 |
8 |
--------------------------------------------------------------------------------
/client/views/users/user_edit.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('user_edit')].helpers({
2 | userProfileEdit: function () {
3 | return userProfileEdit;
4 | },
5 | getTemplate: function () {
6 | return getTemplate(this.template);
7 | }
8 | });
9 |
--------------------------------------------------------------------------------
/client/views/users/user_email.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{#with user}}
4 |
5 | {{_ "please_fill_in_your_email_below_to_finish_signing_up"}}
6 |
7 |
23 | {{/with}}
24 |
25 |
--------------------------------------------------------------------------------
/client/views/users/user_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{> avatar user=this shape="circle"}}
4 |
5 | {{displayName}}
6 |
7 | {{getEmail}}
8 |
9 | {{createdAtFormatted}}
10 | {{postCount}}
11 | {{commentCount}}
12 | {{getKarma}}
13 |
14 | {{#if invites}}
15 | {{_ "invited"}} {{invitedCount}} {{_ "users"}}:
16 |
21 | {{/if}}
22 | ({{inviteCount}} {{_ "invites_left"}})
23 |
24 | {{#if isInvited}} {{/if}}
25 | {{#if userIsAdmin}} {{/if}}
26 |
27 |
32 |
33 |
34 |
35 |
--------------------------------------------------------------------------------
/client/views/users/user_profile.html:
--------------------------------------------------------------------------------
1 |
2 | {{#with user}}
3 | {{#each userProfileDisplay}}
4 | {{> UI.dynamic template=getTemplate data=..}}
5 | {{/each}}
6 | {{/with}}
7 |
8 |
--------------------------------------------------------------------------------
/client/views/users/user_profile.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('user_profile')].helpers({
2 | userProfileDisplay: function () {
3 | return userProfileDisplay;
4 | },
5 | getTemplate: function () {
6 | return getTemplate(this.template);
7 | }
8 | });
--------------------------------------------------------------------------------
/client/views/users/users.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('users')].helpers({
2 | user_item: function () {
3 | return getTemplate('user_item');
4 | },
5 | loadMoreUrl: function(){
6 | var count = parseInt(Session.get('usersLimit')) + 20;
7 | return '/all-users/' + count + '?filterBy='+this.filterBy+'&sortBy='+this.sortBy;
8 | },
9 | allPostsLoaded: function () {
10 | return false;
11 | //TODO: hide load more button when all users have been loaded
12 | },
13 | activeClass: function (link) {
14 | if(link == this.filterBy || link == this.sortBy)
15 | return "active";
16 | },
17 | sortBy: function (parameter) {
18 | return "?filterBy="+this.filterBy+"&sortBy="+parameter;
19 | },
20 | filterBy: function (parameter) {
21 | return "?filterBy="+parameter+"&sortBy="+this.sortBy;
22 | }
23 | });
--------------------------------------------------------------------------------
/collections/events.js:
--------------------------------------------------------------------------------
1 | var eventSchema = new SimpleSchema({
2 | createdAt: {
3 | type: Date
4 | },
5 | name: {
6 | type: String
7 | },
8 | description: {
9 | type: String,
10 | optional: true
11 | },
12 | unique: {
13 | type: Boolean,
14 | optional: true
15 | },
16 | important: { // marking an event as important means it should never be erased
17 | type: Boolean,
18 | optional: true
19 | }
20 | });
21 |
22 |
23 | Events = new Meteor.Collection('events');
24 | Events.attachSchema(eventSchema);
25 |
26 | if (Meteor.isServer) {
27 | logEvent = function (event) {
28 |
29 | // if event is supposed to be unique, check if it has already been logged
30 | if (!!event.unique && !!Events.findOne({name: event.name})) {
31 | return
32 | }
33 |
34 | event.createdAt = new Date();
35 |
36 | Events.insert(event);
37 |
38 | }
39 | }
--------------------------------------------------------------------------------
/collections/messages.js:
--------------------------------------------------------------------------------
1 | if(Meteor.isClient){
2 | // Local (client-only) collection
3 | Messages = new Meteor.Collection(null);
4 |
5 | flashMessage = function(message, type){
6 | type = (typeof type === 'undefined') ? 'error': type;
7 | // Store errors in the 'Messages' local collection
8 | Messages.insert({message:message, type:type, seen: false, show:true});
9 | };
10 |
11 | clearSeenMessages = function(){
12 | Messages.update({seen:true}, {$set: {show:false}}, {multi:true});
13 | };
14 |
15 | }
--------------------------------------------------------------------------------
/lib/config/avatar.js:
--------------------------------------------------------------------------------
1 | Avatar.options = {
2 | fallbackType: 'initials',
3 | emailHashProperty: 'email_hash'
4 | };
5 |
--------------------------------------------------------------------------------
/lib/config/debug.js:
--------------------------------------------------------------------------------
1 | // SimpleSchema.debug = true;
--------------------------------------------------------------------------------
/lib/debug.js:
--------------------------------------------------------------------------------
1 | clog = function (s) {
2 | if(getSetting('debug', false))
3 | console.log(s);
4 | }
--------------------------------------------------------------------------------
/lib/events.js:
--------------------------------------------------------------------------------
1 | trackEvent = function(event, properties){
2 | // console.log('trackevent: ', event, properties);
3 | var properties= (typeof properties === 'undefined') ? {} : properties;
4 | //TODO
5 | // add event to an Events collection for logging and buffering purposes
6 | if(Meteor.isClient){
7 | if(typeof mixpanel !== 'undefined' && typeof mixpanel.track !== 'undefined'){
8 | mixpanel.track(event, properties);
9 | }
10 | if(typeof GoSquared !== 'undefined' && typeof GoSquared.DefaultTracker !== 'undefined'){
11 | GoSquared.DefaultTracker.TrackEvent(event, JSON.stringify(properties));
12 | }
13 | }
14 | };
--------------------------------------------------------------------------------
/lib/publications.js:
--------------------------------------------------------------------------------
1 | privacyOptions = { // true means exposed
2 | _id: true,
3 | commentCount: true,
4 | createdAt: true,
5 | email_hash: true,
6 | isInvited: true,
7 | karma: true,
8 | postCount: true,
9 | slug: true,
10 | username: true,
11 | 'profile.name': true,
12 | 'profile.notifications': true,
13 | 'profile.bio': true,
14 | 'profile.github': true,
15 | 'profile.site': true,
16 | 'profile.twitter': true,
17 | 'services.twitter.profile_image_url': true,
18 | 'services.facebook.id': true,
19 | 'services.twitter.screenName': true,
20 | 'services.github.screenName': true, // Github is not really used, but there are some mentions to it in the code
21 | 'votes.downvotedComments': true,
22 | 'votes.downvotedPosts': true,
23 | 'votes.upvotedComments': true,
24 | 'votes.upvotedPosts': true
25 | };
26 |
27 | // minimum required properties to display avatars
28 | avatarOptions = {
29 | _id: true,
30 | email_hash: true,
31 | slug: true,
32 | username: true,
33 | 'profile.name': true,
34 | 'profile.github': true,
35 | 'profile.twitter': true,
36 | 'services.twitter.profile_image_url': true,
37 | 'services.facebook.id': true,
38 | 'services.twitter.screenName': true,
39 | 'services.github.screenName': true, // Github is not really used, but there are some mentions to it in the code
40 | }
41 |
--------------------------------------------------------------------------------
/lib/router/comments.js:
--------------------------------------------------------------------------------
1 | // Controller for comment pages
2 |
3 | CommentPageController = RouteController.extend({
4 | waitOn: function() {
5 | return [
6 | coreSubscriptions.subscribe('singleCommentAndChildren', this.params._id),
7 | coreSubscriptions.subscribe('commentUsers', this.params._id),
8 | coreSubscriptions.subscribe('commentPost', this.params._id)
9 | ];
10 | },
11 | data: function() {
12 | return {
13 | comment: Comments.findOne(this.params._id)
14 | };
15 | },
16 | onAfterAction: function () {
17 | window.queueComments = false;
18 | },
19 | fastRender: true
20 | });
21 |
22 | Meteor.startup( function () {
23 |
24 | // Comment Reply
25 |
26 | Router.route('/comments/:_id', {
27 | name: 'comment_reply',
28 | template: getTemplate('comment_reply'),
29 | controller: CommentPageController,
30 | onAfterAction: function() {
31 | window.queueComments = false;
32 | }
33 | });
34 |
35 | // Comment Edit
36 |
37 | Router.route('/comments/:_id/edit', {
38 | name: 'comment_edit',
39 | template: getTemplate('comment_edit'),
40 | controller: CommentPageController,
41 | onAfterAction: function() {
42 | window.queueComments = false;
43 | }
44 | });
45 |
46 | });
--------------------------------------------------------------------------------
/lib/router/config.js:
--------------------------------------------------------------------------------
1 | Router.setTemplateNameConverter(function (str) { return str; });
2 |
3 | preloadSubscriptions.push('settings');
4 | preloadSubscriptions.push('currentUser');
5 |
6 | Router.configure({
7 | layoutTemplate: getTemplate('layout'),
8 | loadingTemplate: getTemplate('loading'),
9 | notFoundTemplate: getTemplate('notFound'),
10 | waitOn: function () {
11 | return _.map(preloadSubscriptions, function(sub){
12 | // can either pass strings or objects with subName and subArguments properties
13 | if (typeof sub === 'object'){
14 | Meteor.subscribe(sub.subName, sub.subArguments);
15 | }else{
16 | Meteor.subscribe(sub);
17 | }
18 | });
19 | }
20 | });
21 |
22 | // adding common subscriptions that's need to be loaded on all the routes
23 | // notification does not included here since it is not much critical and
24 | // it might have considerable amount of docs
25 | if(Meteor.isServer) {
26 | FastRender.onAllRoutes(function() {
27 | var router = this;
28 | _.each(preloadSubscriptions, function(sub){
29 | router.subscribe(sub);
30 | });
31 | });
32 | }
33 |
--------------------------------------------------------------------------------
/lib/router/other.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function (){
2 |
3 | // Settings
4 |
5 | Router.route('/settings', {
6 | name: 'settings',
7 | template: getTemplate('settingsForm'),
8 | data: function () {
9 | // we only have one set of settings for now
10 | return {
11 | hasSettings: !!Settings.find().count(),
12 | settings: Settings.findOne()
13 | }
14 | }
15 | });
16 |
17 | // Loading (for testing purposes)
18 |
19 | Router.route('/loading', {
20 | name: 'loading',
21 | template: getTemplate('loading')
22 | });
23 |
24 | // Toolbox
25 |
26 | Router.route('/toolbox', {
27 | name: 'toolbox',
28 | template: getTemplate('toolbox')
29 | });
30 |
31 | });
--------------------------------------------------------------------------------
/lib/version.js:
--------------------------------------------------------------------------------
1 | telescopeVersion = "0.14.0";
--------------------------------------------------------------------------------
/license.md:
--------------------------------------------------------------------------------
1 | The MIT License (MIT)
2 |
3 | Copyright (c) [year] [fullname]
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
--------------------------------------------------------------------------------
/packages.json:
--------------------------------------------------------------------------------
1 | {
2 | }
--------------------------------------------------------------------------------
/packages/.gitignore:
--------------------------------------------------------------------------------
1 | /bootstrap3-datepicker
2 | /npm-container
--------------------------------------------------------------------------------
/packages/npm-container/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/npm-container/index.js:
--------------------------------------------------------------------------------
1 | Meteor.npmRequire = function(moduleName) { // 74
2 | var module = Npm.require(moduleName); // 75
3 | return module; // 76
4 | }; // 77
5 | // 78
6 | Meteor.require = function(moduleName) { // 79
7 | console.warn('Meteor.require is deprecated. Please use Meteor.npmRequire instead!'); // 80
8 | return Meteor.npmRequire(moduleName); // 81
9 | }; // 82
--------------------------------------------------------------------------------
/packages/npm-container/versions.json:
--------------------------------------------------------------------------------
1 | {
2 | "dependencies": [
3 | [
4 | "meteor",
5 | "1.1.3"
6 | ],
7 | [
8 | "underscore",
9 | "1.0.1"
10 | ]
11 | ],
12 | "pluginDependencies": [],
13 | "toolVersion": "meteor-tool@1.0.36",
14 | "format": "1.0"
15 | }
--------------------------------------------------------------------------------
/packages/telescope-api/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-api/lib/server/routes.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | Router.route('api', {
4 | where: 'server',
5 | path: '/api/:limit?',
6 | action: function() {
7 | var limit = parseInt(this.params.limit);
8 | this.response.write(serveAPI(limit));
9 | this.response.end();
10 | }
11 | });
12 |
13 | });
--------------------------------------------------------------------------------
/packages/telescope-api/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({summary: "Telescope API package"});
2 |
3 | Package.onUse(function (api) {
4 |
5 | api.use(['telescope-base', 'telescope-lib'], ['server']);
6 |
7 | api.add_files(['lib/server/api.js', 'lib/server/routes.js'], ['server']);
8 |
9 | api.export(['serveAPI']);
10 |
11 | });
--------------------------------------------------------------------------------
/packages/telescope-base/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-base/lib/base_client.js:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-base/lib/base_client.js
--------------------------------------------------------------------------------
/packages/telescope-base/lib/base_server.js:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-base/lib/base_server.js
--------------------------------------------------------------------------------
/packages/telescope-blank/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-blank/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string",
3 | "customViewLink": "Custom View Link",
4 | "customAdminLink": "Custom Admin Link"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/client/stylesheets/custom.scss:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-blank/lib/client/stylesheets/custom.scss
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/client/templates/customPostTitle.html:
--------------------------------------------------------------------------------
1 |
2 | This is a custom postTitle template
3 |
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/client/templates/custom_template.html:
--------------------------------------------------------------------------------
1 |
2 | Custom Template
3 |
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/client/templates/custom_template.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | Template[getTemplate('customTemplate')].helpers({
4 | name: function () {
5 | return "Bruce Willis";
6 | }
7 | });
8 |
9 | });
10 |
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/custom_fields.js:
--------------------------------------------------------------------------------
1 | // Custom Post Property
2 |
3 | var customProperty = {
4 | propertyName: 'customProperty',
5 | propertySchema: {
6 | type: String, // property type
7 | label: 'customLabel', // key string used for internationalization
8 | optional: true, // make this property optional
9 | autoform: {
10 | editable: true, // make this property editable by users
11 | type: "bootstrap-datetimepicker", // assign a custom input type
12 | omit: false // set to true to omit field from form entirely
13 | }
14 | }
15 | }
16 | addToPostSchema.push(customProperty);
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/main.js:
--------------------------------------------------------------------------------
1 | // Global Function
2 |
3 | myFunction = function (a, b) {
4 | return a + b;
5 | }
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/routes.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | Router.route('/custom-path', {
4 | name: 'customRoute',
5 | template: getTemplate('customTemplate')
6 | });
7 |
8 | });
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/server/publications.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('customPublication', function (limit) {
2 | return Posts.find({}, {limit: limit});
3 | });
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/settings.js:
--------------------------------------------------------------------------------
1 | // Custom Setting
2 |
3 | var customSetting = {
4 | propertyName: 'customSetting',
5 | propertySchema: {
6 | type: String,
7 | optional: true,
8 | autoform: {
9 | group: 'customGroup', // assign custom group (fieldset) in Settings form
10 | private: true // mark as private (not published to client)
11 | }
12 | }
13 | }
14 | addToSettingsSchema.push(customSetting);
--------------------------------------------------------------------------------
/packages/telescope-blank/lib/templates.js:
--------------------------------------------------------------------------------
1 | // Override "postTitle" template
2 |
3 | templates["postTitle"] = "customPostTitle";
--------------------------------------------------------------------------------
/packages/telescope-blank/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-daily/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "daily": "Daily"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "daily": "Daily",
3 | "day_by_day_view": "The most popular posts of each day.",
4 | "load_next_days": "Load Next Days"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/i18n/es.i18n.json:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-daily/i18n/es.i18n.json
--------------------------------------------------------------------------------
/packages/telescope-daily/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "daily": "Jour par jour"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "daily": "Daily"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "daily": "Daily"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/lib/client/stylesheets/daily.scss:
--------------------------------------------------------------------------------
1 | .posts-day-heading{
2 | font-size: 16px;
3 | color: rgba(0,0,0,0.5);
4 | margin: 0 0 10px 0;
5 | }
6 | .empty-day-notice{
7 | padding: 15px;
8 | }
9 | .posts-day .post:last-child{
10 | border-radius: 0 0 3px 3px;
11 | }
12 | .load-more-days-button{
13 | display: block;
14 | background: none;
15 | width:100%;
16 | text-align:center;
17 | font-size:18px;
18 | padding: 0px;
19 | text-align: center;
20 | margin: 20px 0;
21 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/lib/client/templates/after_day.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/packages/telescope-daily/lib/client/templates/before_day.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/packages/telescope-daily/lib/client/templates/posts_daily.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{#each days}}
4 | {{> Template.dynamic template=before_day}}
5 |
{{formatDate date "dddd, MMMM Do YYYY"}}
6 |
7 | {{> Template.dynamic template=singleDay data=context}}
8 |
9 | {{> Template.dynamic template=after_day}}
10 | {{/each}}
11 |
{{_ "load_next_days"}}
12 |
13 |
14 |
--------------------------------------------------------------------------------
/packages/telescope-daily/lib/client/templates/posts_daily.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | Template[getTemplate('postsDaily')].helpers({
4 | days: function () {
5 | var daysArray = [];
6 | // var days = this.days;
7 | var days = Session.get('postsDays');
8 | for (i = 0; i < days; i++) {
9 | daysArray.push({
10 | date: moment().subtract(i, 'days').startOf('day').toDate(),
11 | index: i
12 | });
13 | }
14 | return daysArray;
15 | },
16 | before_day: function () {
17 | return getTemplate('beforeDay');
18 | },
19 | singleDay: function () {
20 | return getTemplate('singleDay');
21 | },
22 | context: function () {
23 | var context = this;
24 | context.showDateNav = false;
25 | return context;
26 | },
27 | after_day: function () {
28 | return getTemplate('afterDay');
29 | },
30 | loadMoreDaysUrl: function () {
31 | var count = parseInt(Session.get('postsDays')) + daysPerPage;
32 | return '/daily/' + count;
33 | }
34 | });
35 |
36 | });
37 |
--------------------------------------------------------------------------------
/packages/telescope-daily/lib/daily.js:
--------------------------------------------------------------------------------
1 | daysPerPage = 5;
2 |
3 | viewsMenu.push({
4 | route: 'postsDaily',
5 | label: 'daily',
6 | description: 'day_by_day_view'
7 | });
--------------------------------------------------------------------------------
/packages/telescope-daily/lib/routes.js:
--------------------------------------------------------------------------------
1 | var coreSubscriptions = new SubsManager({
2 | // cache recent 50 subscriptions
3 | cacheLimit: 50,
4 | // expire any subscription after 30 minutes
5 | expireIn: 30
6 | });
7 |
8 | PostsDailyController = RouteController.extend({
9 |
10 | template: function() {
11 | // use a function to make sure the template is evaluated *after* any template overrides
12 | return getTemplate('postsDaily');
13 | },
14 |
15 | subscriptions: function () {
16 | // this.days = this.params.days ? this.params.days : daysPerPage;
17 | // TODO: find a way to preload the first n posts of the first 5 days?
18 | },
19 |
20 | data: function () {
21 | this.days = this.params.days ? this.params.days : daysPerPage;
22 | Session.set('postsDays', this.days);
23 | return {
24 | days: this.days
25 | };
26 | },
27 |
28 | getTitle: function () {
29 | return i18n.t('daily') + ' - ' + getSetting('title', "Telescope");
30 | },
31 |
32 | getDescription: function () {
33 | return i18n.t('day_by_day_view');
34 | },
35 |
36 | fastRender: true
37 | });
38 |
39 | Meteor.startup(function () {
40 |
41 | Router.route('/daily/:days?', {
42 | name: 'postsDaily',
43 | controller: PostsDailyController
44 | });
45 |
46 | });
--------------------------------------------------------------------------------
/packages/telescope-daily/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-daily/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({summary: "Telescope daily view"});
2 |
3 | Package.onUse(function (api) {
4 |
5 | api.use([
6 | 'telescope-lib',
7 | 'telescope-base',
8 | 'iron:router',
9 | 'meteorhacks:fast-render',
10 | 'meteorhacks:subs-manager',
11 | 'tap:i18n',
12 | 'telescope-singleday',
13 | 'fourseven:scss'
14 | ], ['client', 'server']);
15 |
16 | api.use([
17 | 'jquery',
18 | 'underscore',
19 | 'templating'
20 | ], 'client');
21 |
22 | api.add_files([
23 | 'package-tap.i18n',
24 | 'lib/daily.js',
25 | 'lib/routes.js',
26 | ], ['client', 'server']);
27 |
28 | api.add_files([
29 | 'lib/client/templates/posts_daily.html',
30 | 'lib/client/templates/after_day.html',
31 | 'lib/client/templates/before_day.html',
32 | 'lib/client/templates/posts_daily.js',
33 | 'lib/client/stylesheets/daily.scss',
34 | ], ['client']);
35 |
36 | api.add_files([
37 | "i18n/de.i18n.json",
38 | "i18n/en.i18n.json",
39 | "i18n/es.i18n.json",
40 | "i18n/fr.i18n.json",
41 | "i18n/it.i18n.json",
42 | "i18n/zh-CN.i18n.json",
43 | ], ["client", "server"]);
44 |
45 | api.export(['PostsDailyController']);
46 | });
--------------------------------------------------------------------------------
/packages/telescope-datetimepicker/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-datetimepicker/autoform-bs-datetimepicker.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
--------------------------------------------------------------------------------
/packages/telescope-datetimepicker/fonts/glyphicons-halflings-regular.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-datetimepicker/fonts/glyphicons-halflings-regular.eot
--------------------------------------------------------------------------------
/packages/telescope-datetimepicker/fonts/glyphicons-halflings-regular.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-datetimepicker/fonts/glyphicons-halflings-regular.ttf
--------------------------------------------------------------------------------
/packages/telescope-datetimepicker/fonts/glyphicons-halflings-regular.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-datetimepicker/fonts/glyphicons-halflings-regular.woff
--------------------------------------------------------------------------------
/packages/telescope-datetimepicker/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({
2 | name: 'telescope-datetimepicker',
3 | summary: 'Custom bootstrap-datetimepicker input type for AutoForm',
4 | version: '1.0.3',
5 | });
6 |
7 | Package.onUse(function(api) {
8 | api.use('templating@1.0.0');
9 | api.use('blaze@2.0.0');
10 | api.use('aldeed:autoform');
11 | api.use('fourseven:scss');
12 | // api.use('jquery');
13 | // api.use('tsega:bootstrap3-datetimepicker');
14 | // api.use('chriswessels:glyphicons-halflings');
15 |
16 | api.addFiles([
17 | 'datetimepicker.scss',
18 | 'autoform-bs-datetimepicker.html',
19 | 'autoform-bs-datetimepicker.js',
20 | 'bootstrap-collapse-transitions.js',
21 | 'fonts/glyphicons-halflings-regular.eot',
22 | 'fonts/glyphicons-halflings-regular.svg',
23 | 'fonts/glyphicons-halflings-regular.ttf',
24 | 'fonts/glyphicons-halflings-regular.woff'
25 | ], 'client');
26 | });
27 |
--------------------------------------------------------------------------------
/packages/telescope-email/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-email/.npm/package/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules
2 |
--------------------------------------------------------------------------------
/packages/telescope-email/.npm/package/README:
--------------------------------------------------------------------------------
1 | This directory and the files immediately inside it are automatically generated
2 | when you change this package's NPM dependencies. Commit the files in this
3 | directory (npm-shrinkwrap.json, .gitignore, and this README) to source control
4 | so that others run the same versions of sub-dependencies.
5 |
6 | You should NOT check in the node_modules directory that Meteor automatically
7 | creates; if you are using git, the .gitignore file tells git to ignore it.
8 |
--------------------------------------------------------------------------------
/packages/telescope-email/.npm/package/npm-shrinkwrap.json:
--------------------------------------------------------------------------------
1 | {
2 | "dependencies": {
3 | "html-to-text": {
4 | "version": "0.1.0",
5 | "dependencies": {
6 | "htmlparser": {
7 | "version": "1.7.7"
8 | },
9 | "underscore": {
10 | "version": "1.7.0"
11 | },
12 | "underscore.string": {
13 | "version": "2.3.3"
14 | },
15 | "optimist": {
16 | "version": "0.6.1",
17 | "dependencies": {
18 | "wordwrap": {
19 | "version": "0.0.2"
20 | },
21 | "minimist": {
22 | "version": "0.0.10"
23 | }
24 | }
25 | }
26 | }
27 | }
28 | }
29 | }
30 |
--------------------------------------------------------------------------------
/packages/telescope-email/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "has_created_a_new_post": "has created a new post"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-email/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "has_created_a_new_post": "has created a new post"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-email/i18n/es.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "has_created_a_new_post": "has created a new post"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-email/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "has_created_a_new_post": "a créé un nouveau post"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-email/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "has_created_a_new_post": "has created a new post"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-email/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "has_created_a_new_post": "has created a new post"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/routes.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | // New user email
4 |
5 | Router.route('/email/new-user/:id?', {
6 | name: 'newUser',
7 | where: 'server',
8 | action: function() {
9 | var user = Meteor.users.findOne(this.params.id);
10 | var emailProperties = {
11 | profileUrl: getProfileUrl(user),
12 | username: getUserName(user)
13 | };
14 | html = getEmailTemplate('emailNewUser')(emailProperties);
15 | this.response.write(buildEmailTemplate(html));
16 | this.response.end();
17 | }
18 | });
19 |
20 | // New post email
21 |
22 | Router.route('/email/new-post/:id?', {
23 | name: 'newPost',
24 | where: 'server',
25 | action: function() {
26 | var post = Posts.findOne(this.params.id);
27 | if (!!post) {
28 | html = getEmailTemplate('emailNewPost')(getPostProperties(post));
29 | } else {
30 | html = "No post found. "
31 | }
32 | this.response.write(buildEmailTemplate(html));
33 | this.response.end();
34 | }
35 | });
36 |
37 |
38 | });
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailAccountApproved.handlebars:
--------------------------------------------------------------------------------
1 | {{username}}, welcome to {{siteTitle}}!
2 |
3 | You've just been invited. Start posting .
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailInvite.handlebars:
--------------------------------------------------------------------------------
1 |
2 | {{invitedBy}}
3 | invited you to join {{communityName}}
4 |
5 |
6 | {{#if newUser}}
7 | Join {{communityName}}
8 | {{else}}
9 | Sign in to {{communityName}}
10 | {{/if}}
11 |
12 |
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailNewComment.handlebars:
--------------------------------------------------------------------------------
1 |
2 | {{comment.author}}
3 | left a new comment on
4 | {{post.title}} :
5 |
6 |
7 |
8 |
9 | {{{body}}}
10 |
11 |
12 |
13 | Discuss
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailNewPendingPost.handlebars:
--------------------------------------------------------------------------------
1 |
2 | {{postAuthorName}}
3 | has a new post pending approval:
4 | {{#if url}}
5 | {{postTitle}}}
6 | {{else}}
7 | {{postTitle}}}
8 | {{/if}}
9 |
10 |
11 | {{#if htmlBody}}
12 |
13 | {{{htmlBody}}}
14 |
15 |
16 | {{/if}}
17 |
18 | Go to post
19 |
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailNewPost.handlebars:
--------------------------------------------------------------------------------
1 |
2 | {{postAuthorName}}
3 | has created a new post:
4 | {{#if url}}
5 | {{postTitle}}}
6 | {{else}}
7 | {{postTitle}}}
8 | {{/if}}
9 |
10 |
11 | {{#if htmlBody}}
12 |
13 | {{{htmlBody}}}
14 |
15 |
16 | {{/if}}
17 |
18 | Discuss
19 |
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailNewReply.handlebars:
--------------------------------------------------------------------------------
1 | {{comment.author}}
2 | has replied to your comment on
3 | {{post.title}} :
4 |
5 |
6 |
7 |
8 | {{{body}}}
9 |
10 |
11 |
12 | Discuss
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailNewUser.handlebars:
--------------------------------------------------------------------------------
1 | A new user account has been created: {{username}}
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailPostApproved.handlebars:
--------------------------------------------------------------------------------
1 |
2 | Congratulations, your post has been approved:
3 |
4 |
5 | {{postTitle}}}
6 |
--------------------------------------------------------------------------------
/packages/telescope-email/lib/server/templates/emailTest.handlebars:
--------------------------------------------------------------------------------
1 | This is just a test
2 |
3 | Sent at {{date}}.
--------------------------------------------------------------------------------
/packages/telescope-email/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_"
4 | }
--------------------------------------------------------------------------------
/packages/telescope-embedly/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-embedly/History.md:
--------------------------------------------------------------------------------
1 | ### v0.2.9
2 |
3 | - Update to Meteor 0.9.0.
4 |
5 | ### v0.2.8
6 |
7 | - Don't display image if it cannot be found.
--------------------------------------------------------------------------------
/packages/telescope-embedly/README.md:
--------------------------------------------------------------------------------
1 | The Telescope [Embedly](http://embed.ly) module.
2 |
3 | More details in [this blog post](http://telesc.pe/blog/extending-telescope-with-embedly-thumbnails/).
4 |
5 | ### Install
6 |
7 | 1. `mrt add telescope-module-embedly`.
8 | 2. Go to the Telescope settings page and add your Embedly API key.
9 |
10 | ### Extra Features
11 |
12 | When linking to videos, the thumbnail becomes clickable and opens the video in a lightbox.
--------------------------------------------------------------------------------
/packages/telescope-embedly/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "thumbnail": "Thumbnail",
3 | "thumbnailUrl": "Thumbnail",
4 | "regenerate_thumbnail": "Regenerate Thumbnail",
5 | "clear_thumbnail": "Clear Thumbnail",
6 | "please_fill_in_embedly_key": "Please fill in your Embedly API key to enable thumbnails."
7 | }
--------------------------------------------------------------------------------
/packages/telescope-embedly/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "thumbnail": "Aperçu",
3 | "thumbnailUrl": "Aperçu",
4 | "regenerate_thumbnail": "Regenerer l'aperçu",
5 | "clear_thumbnail": "Effacer l'aperçu",
6 | "please_fill_in_embedly_key": "Veuillez fournir une clé API Embedly pour activer les aperçus."
7 | }
--------------------------------------------------------------------------------
/packages/telescope-embedly/lib/client/autoform-postthumbnail.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if embedlyKeyExists}}
3 |
4 |
5 |
{{>spinner}}
6 |
7 |
8 | {{_ 'regenerate_thumbnail'}}
9 | {{_ 'clear_thumbnail'}}
10 | {{else}}
11 | {{_ "please_fill_in_embedly_key"}}
12 | {{/if}}
13 |
--------------------------------------------------------------------------------
/packages/telescope-embedly/lib/client/post_thumbnail.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if thumbnailUrl}}
3 |
4 |
5 |
6 |
7 |
8 | {{/if}}
9 | {{#if media}}
10 | {{> UI.dynamic template=videoTemplate data=this}}
11 | {{/if}}
12 |
--------------------------------------------------------------------------------
/packages/telescope-embedly/lib/client/post_thumbnail.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postThumbnail')].helpers({
2 | postLink: function () {
3 | return !!this.url ? getOutgoingUrl(this.url) : "/posts/"+this._id;
4 | },
5 | playVideoClass: function () {
6 | return !!this.media ? 'post-thumbnail-has-video': '';
7 | },
8 | videoTemplate: function () {
9 | return getTemplate('postVideo');
10 | }
11 | });
12 |
13 | Template[getTemplate('postThumbnail')].events({
14 | 'click .post-thumbnail-has-video': function (e) {
15 | e.preventDefault();
16 | $('body').addClass('showing-lightbox');
17 | $(e.target).parents('.post').find('.post-video-lightbox').fadeIn('fast');
18 | }
19 | })
--------------------------------------------------------------------------------
/packages/telescope-embedly/lib/client/post_video.html:
--------------------------------------------------------------------------------
1 |
2 | {{#with media}}
3 |
4 |
×
5 |
6 | {{{html}}}
7 |
8 |
9 | {{/with}}
10 |
--------------------------------------------------------------------------------
/packages/telescope-embedly/lib/client/post_video.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('postVideo')].events({
2 | 'click .post-video-lightbox-hide, click .post-video-lightbox': function (e) {
3 | e.preventDefault();
4 | $(e.target).parents('.post').find('.post-video-lightbox').fadeOut('fast');
5 | $('body').removeClass('showing-lightbox');
6 | }
7 | })
--------------------------------------------------------------------------------
/packages/telescope-embedly/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-embedly/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({
2 | summary: "Telescope Embedly module package",
3 | version: '0.2.9',
4 | name: "telescope-embedly",
5 | git: 'https://github.com/TelescopeJS/Telescope-Module-Embedly.git'
6 | });
7 |
8 | Package.onUse( function(api) {
9 |
10 | api.versionsFrom("METEOR@0.9.0");
11 |
12 | api.use([
13 | 'telescope-lib',
14 | 'telescope-base',
15 | 'aldeed:autoform',
16 | 'tap:i18n',
17 | 'fourseven:scss',
18 | 'templating',
19 | 'http'
20 | ]);
21 |
22 | api.add_files([
23 | 'package-tap.i18n',
24 | 'lib/embedly.js'
25 | ], ['client', 'server']);
26 |
27 | api.add_files([
28 | 'lib/server/get_embedly_data.js'
29 | ], ['server']);
30 |
31 | api.add_files([
32 | 'lib/client/autoform-postthumbnail.html',
33 | 'lib/client/autoform-postthumbnail.js',
34 | 'lib/client/post_thumbnail.html',
35 | 'lib/client/post_thumbnail.js',
36 | 'lib/client/post_thumbnail.scss',
37 | 'lib/client/post_video.html',
38 | 'lib/client/post_video.js'
39 | ], ['client']);
40 |
41 | api.add_files([
42 | "i18n/en.i18n.json",
43 | "i18n/fr.i18n.json"
44 | ], ["client", "server"]);
45 | });
--------------------------------------------------------------------------------
/packages/telescope-getting-started/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-getting-started/content/customizing_telescope.md:
--------------------------------------------------------------------------------
1 | ### Changing Colors
2 |
3 | Telescope is fairly flexible out of the box. You can tweak colors for the header and buttons in the [Settings](/settings) panel.
4 |
5 | ### Enabling Thumbnails
6 |
7 | If you'd like, you can also enable post thumbnails. You'll need to get an [Embedly](http://embed.ly) API key first, and then simply add it in the Settings screen.
8 |
9 | ### Enabling The Newsletter
10 |
11 | Telescope can also automatically generate and send a newsletter of the best posts of the day or week. All you need to do is provide your MailChimp API key and list ID in the Settings screen, choose the sending frequency, and then enable the newsletter.
12 |
13 | If you want to learn more, be sure to check out the [Email](http://www.telesc.pe/docs/packages/email/) section of the documentation as well.
14 |
15 | ### Customizing Your Templates
16 |
17 | Telescope also makes it possible to completely override any part of your app with your own custom templates.
18 |
19 | As usual, you'll learn more about this in [the documentation](http://www.telesc.pe/docs/customizing/theming-telescope/).
--------------------------------------------------------------------------------
/packages/telescope-getting-started/content/deploying_telescope.md:
--------------------------------------------------------------------------------
1 | ### Quick Deploy
2 |
3 | Once you've played around with Telescope, you might want to deploy your app for the whole world to see.
4 |
5 | You can do so easily using Meteor's own free hosting service. Just open a terminal window, go to your Telescope app's directory, and type:
6 |
7 | ```
8 | meteor deploy my-app
9 | ```
10 |
11 | Where `my-app` is a unique name you'll pick for your Telescope app. It will then be deployed to `http://my-app.meteor.com`.
12 |
13 | You might need to create a Meteor account first. Just follow the instructions!
14 |
15 | Note that deploying does *not* copy over your database, which contains your posts and settings. So you'll need to configure them separately on your remote Telescope instance.
16 |
17 | ### Deploying For Production
18 |
19 | Hosting on `*.meteor.com` is fine for small apps and prototypes, but if you want to deploy your app in production you'll need something better.
20 |
21 | Check out [the Telescope documentation](http://www.telesc.pe/docs/getting-started/deploying/) to learn more about this topic.
--------------------------------------------------------------------------------
/packages/telescope-getting-started/content/getting_help.md:
--------------------------------------------------------------------------------
1 | ### Stack Overflow
2 |
3 | The best place to ask for help with specific Telescope questions is [Stack Overflow](http://stackoverflow.com/questions/tagged/telescope). Just make sure you use the `telescope` tag!
4 |
5 | ### Telescope Meta
6 |
7 | If you don't have a question, but instead want to discuss a specific aspect of Telescope (or show the world your new Telescope site!), feel free to open a topic on [Telescope Meta](http://meta.telesc.pe).
8 |
9 | ### GitHub Issues
10 |
11 | Finally, if you've found a bug in Telescope, then you should [leave an issue on GitHub](https://github.com/TelescopeJS/Telescope/issues).
--------------------------------------------------------------------------------
/packages/telescope-getting-started/content/images/stackoverflow.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-getting-started/content/images/stackoverflow.png
--------------------------------------------------------------------------------
/packages/telescope-getting-started/content/images/telescope.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-getting-started/content/images/telescope.png
--------------------------------------------------------------------------------
/packages/telescope-getting-started/content/read_this_first.md:
--------------------------------------------------------------------------------
1 | ### Welcome to Telescope!
2 |
3 | If you're reading this, it means you've successfully got Telescope to run.
4 |
5 | To make your first run a bit easier, we've taken the liberty of preloading your brand new app with a few posts that will walk you through your first steps with Telescope.
6 |
7 | ### 1. Creating An Account
8 |
9 | The first thing you'll need to do is create your account. Since this will be the first ever account created in this app, it will automatically be assigned admin rights, and you'll then be able to access Telescope's settings panel.
10 |
11 | Click the “Sign Up” link in the top menu and come back here once you're done!
12 |
13 | ### 2. Configuring Settings
14 |
15 | The next step is configuring a few basic settings, such as your site's title, logo, or language. Don't worry, you can change all of these at any time!
16 |
17 | To do so, go to the “Admin” menu and click on “Settings”.
18 |
19 | ### 3. Start Posting!
20 |
21 | You're now all set to start using Telescope. Check out the other posts for more information, or just start posting!
--------------------------------------------------------------------------------
/packages/telescope-getting-started/content/removing_getting_started_posts.md:
--------------------------------------------------------------------------------
1 | ### Removing Getting Started Posts
2 |
3 | If you're ready to insert your own content and want to delete these getting started posts, comments, and users, you can do so with a single command.
4 |
5 | Just make sure you're logged in, then open your [browser console](http://webmasters.stackexchange.com/questions/8525/how-to-open-the-javascript-console-in-different-browsers) and type:
6 |
7 | ```js
8 | Meteor.call('removeGettingStartedContent');
9 | ```
10 |
11 | See you on the other side!
--------------------------------------------------------------------------------
/packages/telescope-getting-started/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-getting-started/lib/getting_started.js:
--------------------------------------------------------------------------------
1 | addToPostSchema.push(
2 | {
3 | propertyName: 'dummySlug',
4 | propertySchema: {
5 | type: String,
6 | optional: true,
7 | autoform: {
8 | omit: true
9 | }
10 | }
11 | }
12 | );
13 |
14 | addToPostSchema.push(
15 | {
16 | propertyName: 'isDummy',
17 | propertySchema: {
18 | type: Boolean,
19 | optional: true,
20 | autoform: {
21 | omit: true
22 | }
23 | }
24 | }
25 | );
26 |
27 | addToCommentsSchema.push(
28 | {
29 | propertyName: 'isDummy',
30 | propertySchema: {
31 | type: Boolean,
32 | optional: true,
33 | autoform: {
34 | omit: true
35 | }
36 | }
37 | }
38 | );
--------------------------------------------------------------------------------
/packages/telescope-getting-started/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-i18n/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-i18n/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({summary: "Telescope i18n package"});
2 |
3 | Package.onUse(function (api) {
4 | api.use(["tap:i18n"], ["client", "server"]);
5 | api.use(["session"], "client");
6 | api.add_files(['i18n.js'], ['client', 'server']);
7 | api.export([
8 | 'i18n',
9 | 'setLanguage'
10 | ]);
11 | });
12 |
--------------------------------------------------------------------------------
/packages/telescope-invites/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-invites/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-invites/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-invites/i18n/es.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-invites/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-invites/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-invites/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "translation_key": "translation string"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-invites/lib/client/templates/user_invites.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
Invites
4 |
5 | {{#if canCurrentUserInvite}}
6 | {{#autoForm schema=invitesSchema id="inviteForm" class="form-block" type="method" meteormethod="inviteUser"}}
7 |
Invite someone
8 |
9 |
Email
10 |
11 | {{> afFieldInput name="invitedUserEmail"}}
12 |
13 |
14 |
15 | {{#if afFieldIsInvalid name="invitedUserEmail"}}
16 | This is not a valid email
17 | {{/if}}
18 |
19 |
20 | {{/autoForm}}
21 | {{/if}}
22 |
23 |
24 |
25 |
26 | Email
27 | Accepted
28 |
29 |
30 |
31 | {{#each invites}}
32 |
33 | {{invitedUserEmail}}
34 | {{#if accepted}} {{/if}}
35 |
36 | {{/each}}
37 |
38 |
39 |
40 |
41 |
--------------------------------------------------------------------------------
/packages/telescope-invites/lib/server/publications.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('invites', function (userId) {
2 | var invites = Invites.find({invitingUserId: userId})
3 | return (this.userId === userId || isAdmin(Meteor.user())) ? invites : []
4 | });
--------------------------------------------------------------------------------
/packages/telescope-invites/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-kadira/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-kadira/lib/kadira-settings.js:
--------------------------------------------------------------------------------
1 | var kadiraAppIdProperty = {
2 | propertyName: 'kadiraAppId',
3 | propertyGroup: 'kadira',
4 | propertySchema: {
5 | type: String,
6 | optional: true,
7 | autoform: {
8 | group: 'kadira'
9 | }
10 | }
11 | }
12 | addToSettingsSchema.push(kadiraAppIdProperty);
13 |
14 | var kadiraAppSecretProperty = {
15 | propertyName: 'kadiraAppSecret',
16 | propertyGroup: 'kadira',
17 | propertySchema: {
18 | type: String,
19 | optional: true,
20 | autoform: {
21 | group: 'kadira',
22 | private: true
23 | }
24 | }
25 | }
26 | addToSettingsSchema.push(kadiraAppSecretProperty);
--------------------------------------------------------------------------------
/packages/telescope-kadira/lib/server/kadira.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function() {
2 | if(!!getSetting('kadiraAppId') && !!getSetting('kadiraAppSecret')){
3 | Kadira.connect(getSetting('kadiraAppId'), getSetting('kadiraAppSecret'));
4 | }
5 | });
--------------------------------------------------------------------------------
/packages/telescope-kadira/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({
2 | summary: "Telescope Kadira package",
3 | version: '0.1.0',
4 | name: "telescope-kadira"
5 | });
6 |
7 | Package.onUse(function (api) {
8 |
9 | api.use([
10 | 'telescope-lib',
11 | 'telescope-base'
12 | ], ['client', 'server']);
13 |
14 | api.use([
15 | 'meteorhacks:kadira@2.14.0'
16 | ], ['server']);
17 |
18 | api.add_files([
19 | 'lib/kadira-settings.js'
20 | ], ['client', 'server']);
21 |
22 | api.add_files([
23 | 'lib/server/kadira.js'
24 | ], ['server']);
25 |
26 | });
--------------------------------------------------------------------------------
/packages/telescope-lib/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-lib/lib/autolink.js:
--------------------------------------------------------------------------------
1 | //https://github.com/bryanwoods/autolink-js
2 | (function(){var a,b=[].slice;a=function(){var j,i,d,f,e,c,g,h;c=1<=arguments.length?b.call(arguments,0):[];g=/(^|\s)(\b(https?):\/\/[\-A-Z0-9+&@#\/%?=~_|!:,.;]*[\-A-Z0-9+&@#\/%=~_|]\b)/ig;if(c.length>0){e=c[0];i=e.callback;if((i!=null)&&typeof i==="function"){j=i;delete e.callback;}f="";for(d in e){h=e[d];f+=" "+d+"='"+h+"'";}return this.replace(g,function(l,o,k){var n,m;m=j&&j(k);n=m||(""+k+" ");return""+o+n;});}else{return this.replace(g,"$1$2 ");}};String.prototype.autoLink=a;}).call(this);
3 |
--------------------------------------------------------------------------------
/packages/telescope-lib/lib/client/jquery.exists.js:
--------------------------------------------------------------------------------
1 | $.fn.exists = function () {
2 | return this.length !== 0;
3 | }
--------------------------------------------------------------------------------
/packages/telescope-lib/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({
2 | summary: "Telescope library package",
3 | version: '0.2.9',
4 | name: "telescope-lib"
5 | });
6 |
7 | Package.onUse(function (api) {
8 |
9 | api.use([
10 | 'underscore'
11 | ], ['client', 'server']);
12 |
13 | api.use([
14 | 'jquery'
15 | ], 'client');
16 |
17 | api.add_files([
18 | 'lib/lib.js',
19 | 'lib/deep.js',
20 | 'lib/deep_extend.js',
21 | 'lib/autolink.js',
22 | 'lib/permissions.js'
23 | ], ['client', 'server']);
24 |
25 | api.add_files(['lib/client/jquery.exists.js'], ['client']);
26 |
27 | api.export([
28 | 'deepExtend',
29 | 'camelToDash',
30 | 'dashToCamel',
31 | 'camelCaseify',
32 | 'getSetting',
33 | 'getThemeSetting',
34 | 'getSiteUrl',
35 | 'trimWords',
36 | 'can',
37 | '_',
38 | 'capitalise'
39 | ]);
40 | });
--------------------------------------------------------------------------------
/packages/telescope-lib/versions.json:
--------------------------------------------------------------------------------
1 | {
2 | "dependencies": [
3 | [
4 | "jquery",
5 | "1.0.1"
6 | ],
7 | [
8 | "meteor",
9 | "1.1.3"
10 | ],
11 | [
12 | "underscore",
13 | "1.0.1"
14 | ]
15 | ],
16 | "pluginDependencies": [],
17 | "toolVersion": "meteor-tool@1.0.36",
18 | "format": "1.0"
19 | }
--------------------------------------------------------------------------------
/packages/telescope-module-share/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-module-share/lib/client/post_share.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
11 |
--------------------------------------------------------------------------------
/packages/telescope-module-share/lib/client/post_share.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('postShare')].helpers({
3 | sourceLink: function(){
4 | return !!this.url ? this.url : getSiteUrl() + "posts/"+this._id;
5 | },
6 | viaTwitter: function () {
7 | return !!getSetting('twitterAccount') ? 'via='+getSetting('twitterAccount') : '';
8 | }
9 | });
10 |
11 | Template[getTemplate('postShare')].events({
12 | 'click .share-link': function(e){
13 | var $this = $(e.target).parents('.post-share').find('.share-link');
14 | var $share = $this.parents('.post-share').find('.share-options');
15 | e.preventDefault();
16 | $('.share-link').not($this).removeClass("active");
17 | $(".share-options").not($share).addClass("hidden");
18 | $this.toggleClass("active");
19 | $share.toggleClass("hidden");
20 | }
21 | });
22 | });
--------------------------------------------------------------------------------
/packages/telescope-module-share/lib/share.js:
--------------------------------------------------------------------------------
1 | postModules.push({
2 | template: 'postShare',
3 | order: 25
4 | });
--------------------------------------------------------------------------------
/packages/telescope-module-share/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({summary: "Telescope share module package"});
2 |
3 | Package.onUse(function (api) {
4 |
5 | api.use(['telescope-lib', 'telescope-base', 'fourseven:scss'], ['client', 'server']);
6 |
7 | api.use([
8 | 'jquery',
9 | 'underscore',
10 | 'templating'
11 | ], 'client');
12 |
13 | api.add_files(['lib/share.js'], ['client', 'server']);
14 |
15 | api.add_files(['lib/client/post_share.html', 'lib/client/post_share.js', 'lib/client/post_share.scss'], ['client']);
16 |
17 | // api.export();
18 | });
--------------------------------------------------------------------------------
/packages/telescope-newsletter/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-newsletter/.npm/package/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules
2 |
--------------------------------------------------------------------------------
/packages/telescope-newsletter/.npm/package/README:
--------------------------------------------------------------------------------
1 | This directory and the files immediately inside it are automatically generated
2 | when you change this package's NPM dependencies. Commit the files in this
3 | directory (npm-shrinkwrap.json, .gitignore, and this README) to source control
4 | so that others run the same versions of sub-dependencies.
5 |
6 | You should NOT check in the node_modules directory that Meteor automatically
7 | creates; if you are using git, the .gitignore file tells git to ignore it.
8 |
--------------------------------------------------------------------------------
/packages/telescope-newsletter/.npm/package/npm-shrinkwrap.json:
--------------------------------------------------------------------------------
1 | {
2 | "dependencies": {
3 | "html-to-text": {
4 | "version": "0.1.0",
5 | "dependencies": {
6 | "htmlparser": {
7 | "version": "1.7.7"
8 | },
9 | "underscore": {
10 | "version": "1.7.0"
11 | },
12 | "underscore.string": {
13 | "version": "2.3.3"
14 | },
15 | "optimist": {
16 | "version": "0.6.1",
17 | "dependencies": {
18 | "wordwrap": {
19 | "version": "0.0.2"
20 | },
21 | "minimist": {
22 | "version": "0.0.10"
23 | }
24 | }
25 | }
26 | }
27 | }
28 | }
29 | }
30 |
--------------------------------------------------------------------------------
/packages/telescope-newsletter/History.md:
--------------------------------------------------------------------------------
1 | ## v0.1.6
2 |
3 | - Return error message or campaign subject for cron job.
4 | - Change Newsletter Frequency option to a `select` input.
5 |
6 | ## v0.1.5
7 |
8 | - Added option to show/hide newsletter sign-up banner
--------------------------------------------------------------------------------
/packages/telescope-newsletter/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "receive_the_best_of": "Receive the best of",
3 | "right_in_your_inbox": "right in your inbox.",
4 | "get_newsletter": "Get Newsletter",
5 | "thanks_for_subscribing": "Thanks for subscribing!"
6 | }
--------------------------------------------------------------------------------
/packages/telescope-newsletter/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "receive_the_best_of": "Receive the best of",
3 | "right_in_your_inbox": "right in your inbox.",
4 | "get_newsletter": "Get Newsletter",
5 | "thanks_for_subscribing": "Thanks for subscribing!",
6 | "newsletter": "newsletter",
7 | "showBanner": "Show Banner",
8 | "mailChimpAPIKey": "MailChimp API Key",
9 | "mailChimpListId": "MailChimp List ID",
10 | "postsPerNewsletter": "Posts per Newsletter",
11 | "newsletterFrequency": "Newsletter Frequency",
12 | "newsletterTime": "Newsletter Time",
13 | "enableNewsletter": "Enable Newsletter",
14 | "autoSubscribe": "Auto Subscribe"
15 | }
--------------------------------------------------------------------------------
/packages/telescope-newsletter/i18n/es.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "receive_the_best_of": "Receive the best of",
3 | "right_in_your_inbox": "right in your inbox.",
4 | "get_newsletter": "Get Newsletter",
5 | "thanks_for_subscribing": "Thanks for subscribing!"
6 | }
--------------------------------------------------------------------------------
/packages/telescope-newsletter/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "receive_the_best_of": "Receive the best of",
3 | "right_in_your_inbox": "right in your inbox.",
4 | "get_newsletter": "Get Newsletter",
5 | "thanks_for_subscribing": "Thanks for subscribing!",
6 | "newsletter": "newsletter",
7 | "showBanner": "Afficher la Bannière",
8 | "mailChimpAPIKey": "Clé API MailChimp",
9 | "mailChimpListId": "ID Liste MailChimp",
10 | "postsPerNewsletter": "Posts par Newsletter",
11 | "newsletterFrequency": "Fréquence de la Newsletter"
12 | }
--------------------------------------------------------------------------------
/packages/telescope-newsletter/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "receive_the_best_of": "Receive the best of",
3 | "right_in_your_inbox": "right in your inbox.",
4 | "get_newsletter": "Get Newsletter",
5 | "thanks_for_subscribing": "Thanks for subscribing!"
6 | }
--------------------------------------------------------------------------------
/packages/telescope-newsletter/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "receive_the_best_of": "Receive the best of",
3 | "right_in_your_inbox": "right in your inbox.",
4 | "get_newsletter": "Get Newsletter",
5 | "thanks_for_subscribing": "Thanks for subscribing!"
6 | }
--------------------------------------------------------------------------------
/packages/telescope-newsletter/lib/client/templates/newsletter_banner.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if showBanner}}
3 |
4 |
11 |
{{_ "thanks_for_subscribing"}}
12 |
×
13 |
14 | {{/if}}
15 |
--------------------------------------------------------------------------------
/packages/telescope-newsletter/lib/server/routes.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | Router.route('/email/campaign', {
4 | name: 'campaign',
5 | where: 'server',
6 | action: function() {
7 | var campaign = buildCampaign(getCampaignPosts(getSetting('postsPerNewsletter', 5)));
8 | var campaignSubject = 'Subject: '+campaign.subject+' (note: contents might change)
';
9 | var campaignSchedule = 'Scheduled for: '+ Meteor.call('getNextJob') +'
';
10 |
11 | this.response.write(campaignSubject+campaignSchedule+campaign.html);
12 | this.response.end();
13 | }
14 | });
15 |
16 | Router.route('/email/digest-confirmation', {
17 | name: 'digestConfirmation',
18 | where: 'server',
19 | action: function() {
20 | var confirmationHtml = getEmailTemplate('emailDigestConfirmation')({
21 | time: 'January 1st, 1901',
22 | newsletterLink: 'http://example.com',
23 | subject: 'Lorem ipsum dolor sit amet'
24 | });
25 | this.response.write(buildEmailTemplate(confirmationHtml));
26 | this.response.end();
27 | }
28 | });
29 |
30 | });
--------------------------------------------------------------------------------
/packages/telescope-newsletter/lib/server/templates/emailDigest.handlebars:
--------------------------------------------------------------------------------
1 |
40 |
41 | Recently on {{siteName}}
42 | – {{date}}
43 |
44 |
45 |
46 | {{{content}}}
47 |
48 |
--------------------------------------------------------------------------------
/packages/telescope-newsletter/lib/server/templates/emailDigestConfirmation.handlebars:
--------------------------------------------------------------------------------
1 | Newsletter scheduled for {{time}}
2 |
3 | {{subject}}
--------------------------------------------------------------------------------
/packages/telescope-newsletter/lib/server/templates/emailPostItem.handlebars:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | {{#if thumbnailUrl}}
6 |
7 | {{/if}}
8 |
9 | {{title}}
10 |
11 |
12 |
13 | {{#if domain}}
14 |
{{domain}}
15 | |
16 | {{/if}}
17 |
Submitted by
18 |
on {{date}}
19 | |
20 |
21 |
22 |
23 |
24 | {{#if body}}
25 |
26 | {{{htmlBody}}}
27 |
28 |
29 | {{/if}}
30 |
31 |
32 |
33 |
34 |
35 |
--------------------------------------------------------------------------------
/packages/telescope-newsletter/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-notifications/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "left_a_new_comment_on": "left a new comment on",
3 | "has_replied_to_your_comment_on": "has replied to your comment on",
4 | "mark_as_read": "Mark as read",
5 | "no_notifications": "No notifications",
6 | "you_have_been_unsubscribed_from_all_notifications": "You have been unsubscribed from all notifications.",
7 | "user_not_found": "User not found",
8 | "1_notification": "1 notification",
9 | "notifications": "notifications"
10 | }
--------------------------------------------------------------------------------
/packages/telescope-notifications/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "left_a_new_comment_on": "left a new comment on",
3 | "has_replied_to_your_comment_on": "has replied to your comment on",
4 | "mark_as_read": "Mark as read",
5 | "no_notifications": "No notifications",
6 | "you_have_been_unsubscribed_from_all_notifications": "You have been unsubscribed from all notifications.",
7 | "user_not_found": "User not found",
8 | "1_notification": "1 notification",
9 | "notifications": "notifications",
10 | "notifications_fieldset": "Notifications",
11 | "emailNotifications": "Email Notifications",
12 | "your_post": "Your post",
13 | "has_been_approved": "has been approved"
14 | }
15 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/i18n/es.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "left_a_new_comment_on": "left a new comment on",
3 | "has_replied_to_your_comment_on": "has replied to your comment on",
4 | "mark_as_read": "Mark as read",
5 | "no_notifications": "No notifications",
6 | "you_have_been_unsubscribed_from_all_notifications": "You have been unsubscribed from all notifications.",
7 | "user_not_found": "User not found",
8 | "1_notification": "1 notification",
9 | "notifications": "notifications"
10 | }
--------------------------------------------------------------------------------
/packages/telescope-notifications/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "left_a_new_comment_on": "a laissé un nouveau commentaire sur",
3 | "has_replied_to_your_comment_on": "a répondu à",
4 | "mark_as_read": "Marquer comme lu",
5 | "no_notifications": "Aucune notification",
6 | "you_have_been_unsubscribed_from_all_notifications": "Vous avez été désabonné de toutes les notifications.",
7 | "user_not_found": "Utilisateur non trouvé",
8 | "1_notification": "1 notification",
9 | "notifications": "notifications",
10 | "emailNotifications": "Notifications par Email",
11 | "your_post": "Votre post",
12 | "has_been_approved": "a été approuvé"
13 | }
--------------------------------------------------------------------------------
/packages/telescope-notifications/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "left_a_new_comment_on": "left a new comment on",
3 | "has_replied_to_your_comment_on": "has replied to your comment on",
4 | "mark_as_read": "Mark as read",
5 | "no_notifications": "No notifications",
6 | "you_have_been_unsubscribed_from_all_notifications": "You have been unsubscribed from all notifications.",
7 | "user_not_found": "User not found",
8 | "1_notification": "1 notification",
9 | "notifications": "notifications"
10 | }
--------------------------------------------------------------------------------
/packages/telescope-notifications/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "left_a_new_comment_on": "left a new comment on",
3 | "has_replied_to_your_comment_on": "has replied to your comment on",
4 | "mark_as_read": "Mark as read",
5 | "no_notifications": "No notifications",
6 | "you_have_been_unsubscribed_from_all_notifications": "You have been unsubscribed from all notifications.",
7 | "user_not_found": "User not found",
8 | "1_notification": "1 notification",
9 | "notifications": "notifications"
10 | }
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/notification_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{timeAgo timestamp}}
4 |
5 | {{{notificationHTML}}}
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/notification_item.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('notificationItem')].helpers({
2 | properties: function(){
3 | return this.data;
4 | },
5 | notificationHTML: function(){
6 | return this.message();
7 | }
8 | });
9 |
10 | Template[getTemplate('notificationItem')].events({
11 | 'click .action-link': function(event, instance){
12 | var notificationId=instance.data._id;
13 | Herald.collection.update(
14 | {_id: notificationId},
15 | {
16 | $set:{
17 | read: true
18 | }
19 | },
20 | function(error, result){
21 | if(error){
22 | console.log(error);
23 | }
24 | }
25 | );
26 | }
27 | });
28 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/notification_new_comment.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{author}}
4 | {{_ "left_a_new_comment_on"}}
5 | {{postTitle}}
6 |
7 |
8 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/notification_new_reply.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{author}}
4 | {{_ "has_replied_to_your_comment_on"}}
5 | {{postTitle}}
6 |
7 |
8 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/notification_post_approved.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{_ "your_post"}}
4 | {{postTitle}}
5 | {{_ "has_been_approved"}}
6 |
7 |
8 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/notifications_menu.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if isLoggedIn}}
3 |
18 | {{/if}}
19 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/unsubscribe.html:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/client/templates/unsubscribe.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('unsubscribe')].created = function(){
2 | var hash = this.data.hash;
3 | Meteor.call('unsubscribeUser', hash, function(error, result){
4 | if(result){
5 | Session.set('unsubscribedMessage', __('you_have_been_unsubscribed_from_all_notifications'));
6 | }else{
7 | Session.set('unsubscribedMessage', __('user_not_found'));
8 | }
9 | });
10 | trackEvent('notificationsUnsubcribe', {hash: hash});
11 | };
12 |
13 | Template[getTemplate('unsubscribe')].helpers({
14 | unsubscribed : function(){
15 | // we have to use a session variable because the string we want to display
16 | // depends on the return value of an asynchronous callback (unsubscribeUser)
17 | return Session.get('unsubscribedMessage');
18 | }
19 | });
--------------------------------------------------------------------------------
/packages/telescope-notifications/lib/server/routes.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | // Notification email
4 |
5 | Router.route('/email/notification/:id?', {
6 | name: 'notification',
7 | where: 'server',
8 | action: function() {
9 | var notification = Herald.collection.findOne(this.params.id);
10 | var notificationContents = buildEmailNotification(notification);
11 | this.response.write(notificationContents.html);
12 | this.response.end();
13 | }
14 | });
15 |
16 | });
--------------------------------------------------------------------------------
/packages/telescope-notifications/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/.npm/package/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules
2 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/.npm/package/README:
--------------------------------------------------------------------------------
1 | This directory and the files immediately inside it are automatically generated
2 | when you change this package's NPM dependencies. Commit the files in this
3 | directory (npm-shrinkwrap.json, .gitignore, and this README) to source control
4 | so that others run the same versions of sub-dependencies.
5 |
6 | You should NOT check in the node_modules directory that Meteor automatically
7 | creates; if you are using git, the .gitignore file tells git to ignore it.
8 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/.npm/package/npm-shrinkwrap.json:
--------------------------------------------------------------------------------
1 | {
2 | "dependencies": {
3 | "he": {
4 | "version": "0.5.0"
5 | },
6 | "htmlparser2": {
7 | "version": "3.8.2",
8 | "dependencies": {
9 | "domhandler": {
10 | "version": "2.3.0"
11 | },
12 | "domutils": {
13 | "version": "1.5.0"
14 | },
15 | "domelementtype": {
16 | "version": "1.1.3"
17 | },
18 | "readable-stream": {
19 | "version": "1.1.13",
20 | "dependencies": {
21 | "core-util-is": {
22 | "version": "1.0.1"
23 | },
24 | "isarray": {
25 | "version": "0.0.1"
26 | },
27 | "string_decoder": {
28 | "version": "0.10.31"
29 | },
30 | "inherits": {
31 | "version": "2.0.1"
32 | }
33 | }
34 | },
35 | "entities": {
36 | "version": "1.0.0"
37 | }
38 | }
39 | },
40 | "to-markdown": {
41 | "version": "0.0.2"
42 | }
43 | }
44 | }
45 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "feed_already_exists": "A feed with the same URL already exists.",
3 | "you_need_to_login_and_be_an_admin_to_add_a_new_feed": "You need to log in and be an admin to add a new feed.",
4 | "import_new_posts_from_feeds": "Import new posts from feeds."
5 | }
6 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/client/routes.js:
--------------------------------------------------------------------------------
1 | adminMenu.push({
2 | route: 'feeds',
3 | label: 'Feeds',
4 | description: 'import_new_posts_from_feeds'
5 | });
6 |
7 | Meteor.startup(function () {
8 |
9 | Router.onBeforeAction(Router._filters.isAdmin, {only: ['feeds']});
10 |
11 | // RSS Urls Admin
12 |
13 | Router.route('/feeds', {
14 | name: 'feeds',
15 | waitOn: function() {
16 | return [
17 | Meteor.subscribe('feeds'),
18 | Meteor.subscribe('allUsersAdmin')
19 | ];
20 | },
21 | template: getTemplate('feeds')
22 | });
23 |
24 | });
25 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/client/scss/feeds.scss:
--------------------------------------------------------------------------------
1 | $light-yellow:#fffcea;
2 |
3 | .add-feed{
4 | background: $light-yellow;
5 | }
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/client/templates/feed_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{> quickForm collection="Feeds" id=formId type="update" doc=this label-class="control-label" input-col-class="controls" template="telescope"}}
4 |
Delete
5 |
6 |
7 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/client/templates/feed_item.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('feedItem')].helpers({
3 | formId: function () {
4 | return 'updateFeed-'+ this._id
5 | }
6 | });
7 |
8 | Template[getTemplate('feedItem')].events({
9 | 'click .delete-link': function(e, instance){
10 | e.preventDefault();
11 | if (confirm("Delete feed?")) {
12 | Feeds.remove(instance.data._id);
13 | }
14 | }
15 | });
16 | });
17 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/client/templates/feeds.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
Add new feed:
4 | {{> quickForm collection="Feeds" id="insertFeedForm" type="insert" label-class="control-label" input-col-class="controls" template="telescope"}}
5 |
6 | {{#each feeds}}
7 | {{> UI.dynamic template=feedItem}}
8 | {{/each}}
9 |
10 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/client/templates/feeds.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('feeds')].helpers({
3 | feeds: function(){
4 | return Feeds.find({}, {sort: {url: 1}});
5 | },
6 | feedItem: function () {
7 | return getTemplate('feedItem');
8 | }
9 | });
10 |
11 | Template[getTemplate('feeds')].events({
12 | 'click input[type=submit]': function(e){
13 | e.preventDefault();
14 |
15 | var url = $('#url').val();
16 |
17 | Meteor.call('insertFeed', {url: url}, function(error, result) {
18 | if(error){
19 | console.log(error);
20 | flashMessage(error.reason, "error");
21 | clearSeenMessages();
22 | }else{
23 | $('#url').val('');
24 | }
25 | });
26 | }
27 | });
28 | });
29 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/server/cron.js:
--------------------------------------------------------------------------------
1 | SyncedCron.options = {
2 | log: false,
3 | collectionName: 'cronHistory',
4 | utc: false,
5 | collectionTTL: 172800
6 | }
7 |
8 | var addJob = function () {
9 | SyncedCron.add({
10 | name: 'Post by RSS feed',
11 | schedule: function(parser) {
12 | return parser.text('every 30 minutes');
13 | },
14 | job: function() {
15 | if (Feeds.find().count()) {
16 | fetchFeeds();
17 | }
18 | }
19 | });
20 | }
21 |
22 | Meteor.startup(function () {
23 | addJob();
24 | })
25 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/lib/server/publications.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('feeds', function() {
2 | if(isAdminById(this.userId)){
3 | return Feeds.find();
4 | }
5 | return [];
6 | });
7 |
--------------------------------------------------------------------------------
/packages/telescope-post-by-feed/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-releases/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-releases/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "telescope_has_been_updated": "Telescope has been updated."
3 | }
--------------------------------------------------------------------------------
/packages/telescope-releases/lib/client/scss/releases.scss:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-releases/lib/client/scss/releases.scss
--------------------------------------------------------------------------------
/packages/telescope-releases/lib/client/templates/current_release.html:
--------------------------------------------------------------------------------
1 |
2 | {{#with currentRelease}}
3 |
4 |
{{_ "telescope_has_been_updated"}}
5 |
6 | {{#markdown}}{{notes}}{{/markdown}}
7 |
8 |
×
9 |
10 | {{/with}}
11 |
--------------------------------------------------------------------------------
/packages/telescope-releases/lib/client/templates/current_release.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | Template[getTemplate('currentRelease')].created = function () {
4 | this.release = function () {
5 | return Releases.find({read: false}).fetch()[0];
6 | }
7 | };
8 |
9 | Template[getTemplate('currentRelease')].helpers({
10 | currentRelease: function () {
11 | return Template.instance().release();
12 | }
13 | });
14 |
15 | Template[getTemplate('currentRelease')].events({
16 | 'click .release-dismiss': function (event, instance) {
17 | event.preventDefault();
18 | Releases.update(instance.release()._id, {$set: {read: true}});
19 | }
20 | })
21 |
22 | });
23 |
--------------------------------------------------------------------------------
/packages/telescope-releases/lib/releases.js:
--------------------------------------------------------------------------------
1 | Releases = new Meteor.Collection('releases');
2 |
3 | heroModules.push({
4 | template: 'currentRelease'
5 | });
6 |
7 | preloadSubscriptions.push('currentRelease');
8 |
9 | Meteor.startup(function () {
10 | Releases.allow({
11 | insert: isAdminById,
12 | update: isAdminById,
13 | remove: isAdminById
14 | });
15 | });
16 |
--------------------------------------------------------------------------------
/packages/telescope-releases/lib/server/import_releases.js:
--------------------------------------------------------------------------------
1 | importRelease = function (number) {
2 | var releaseNotes = Assets.getText("releases/" + number + ".md");
3 |
4 | if (!Releases.findOne({number: number})) {
5 |
6 | release = {
7 | number: number,
8 | notes: releaseNotes,
9 | createdAt: new Date(),
10 | read: false
11 | }
12 | Releases.insert(release);
13 |
14 | } else {
15 |
16 | // if release note already exists, update its content in case it's been updated
17 | Releases.update({number: number}, {$set: {notes: releaseNotes}})
18 |
19 | }
20 | };
21 |
22 | Meteor.startup(function () {
23 |
24 | importRelease('0.11.0');
25 | importRelease('0.11.1');
26 | importRelease('0.12.0');
27 | importRelease('0.13.0');
28 | importRelease('0.14.0');
29 |
30 | // if this is before the first run, mark all release notes as read to avoid showing them
31 | if (!Events.findOne({name: 'firstRun'})) {
32 | var r = Releases.update({}, {$set: {read: true}}, {multi: true});
33 | }
34 |
35 | });
--------------------------------------------------------------------------------
/packages/telescope-releases/lib/server/publications.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('currentRelease', function() {
2 | if(isAdminById(this.userId)){
3 | return Releases.find({}, {sort: {createdAt: -1}, limit: 1});
4 | }
5 | return [];
6 | });
--------------------------------------------------------------------------------
/packages/telescope-releases/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-releases/releases/0.11.0.md:
--------------------------------------------------------------------------------
1 | ### v0.11.0 “AvatarScope”
2 |
3 | * Added new `userCreatedCallbacks` callback hook.
4 | * Added new setting to subscribe new user to mailing list automatically.
5 | * Added new `debug` setting.
6 | * `siteUrl` setting now affects `Meteor.absoluteUrl()`.
7 | * Added new `clog` function that only logs if `debug` setting is true.
8 | * Simplified post module system, modules are not split in three zones anymore.
9 | * Added new `postThumbnail` hook to show Embedly thumbnail.
10 | * Simplified Hubble theme CSS for both desktop and mobile.
11 | * Many CSS tweaks for Hubble mobile.
12 | * Show author and commenters avatars on post item.
13 | * Adding description to post list pages and showing them in menus.
14 | * Improved Russian translation (thanks @Viktorminator!).
15 | * Now using `editorconfig` (thanks @erasaur!).
16 | * Upgraded to `useraccounts:unstyled@1.4.0` (thanks @splendido!).
--------------------------------------------------------------------------------
/packages/telescope-releases/releases/0.11.1.md:
--------------------------------------------------------------------------------
1 | ### v0.11.1 “FeedScope”
2 |
3 | * Post submit and edit forms now submit to their respective methods directly.
4 | * Removed `postSubmitRenderedCallbacks` and `postEditRenderedCallbacks`.
5 | * `telescope-post-by-feed` package now lets you import posts from RSS feeds.
6 | * Adding limit of 200 posts to post list request.
7 | * Refactoring post and comment submit to fix latency compensation issues.
8 | * Tags package now using Autoform.
--------------------------------------------------------------------------------
/packages/telescope-releases/releases/0.12.0.md:
--------------------------------------------------------------------------------
1 | ### v0.12.0 “DummyScope”
2 |
3 | Important: existing newsletters and feeds need to be manually re-enabled in the Settings panel.
4 |
5 | * Added "Enable Newsletter" setting. Note: existing newsletters must be re-enabled.
6 | * Added "Enable Feeds" settings. Note: existing feeds must be re-enabled.
7 | * Now showing release notes for latest version right inside the app.
8 | * Added dummy posts, users, and comments.
9 | * Added new Events collection for keeping track of important events.
10 | * Log first run event.
11 | * `MAIL_URL` environment variable can now be set from Settings.
12 | * Renamed `viewNav` to `viewsMenu`.
13 | * Renamed `adminNav` to `adminMenu`.
14 | * **New and improved [documentation](http://telesc.pe/docs).**
--------------------------------------------------------------------------------
/packages/telescope-releases/releases/0.13.0.md:
--------------------------------------------------------------------------------
1 | ### v0.13.0 “ComponentScope”
2 |
3 | * Tweaked comments layout in Hubbble theme.
4 | * Added Bulgarian translation (thanks @toome123!).
5 | * Cleaned up permission functions (thanks @anthonymayer!).
6 | * Various fixes (thanks @comerc and @Kikobeats!).
7 | * Stopped synced-cron message logging.
8 | * Limit all posts lists to 200 posts.
9 | * Refactored posts lists to use the template-level subscription pattern when appropriate.
10 | * Refactored `single day` and `daily` packages.
11 | * Footer field now accepts Markdown instead of HTML.
12 | * Feeds can now be assigned to a user.
13 | * Various CSS tweaks.
14 | * Fixing newsletter issue.
15 | * Post rank now has its own module.
16 | * Changed how field label i18n works.
--------------------------------------------------------------------------------
/packages/telescope-releases/releases/0.14.0.md:
--------------------------------------------------------------------------------
1 | ### v0.14.0 “GridScope”
2 |
3 | * Adeed Grid Layout option.
4 | * Cleaned up vote click handling functions and added tests (thanks @anthonymayer!).
5 | * Added `threadModules` zone.
6 | * Added `upvoteCallbacks` and `downvoteCallbacks` callback arrays.
7 | * Fix “post awaiting moderation” message bug.
8 | * You can now subscribe to comment threads (thanks @delgermurun!).
9 | * Added `postApproveCallbacks` callback array.
10 | * Added notifications for pending and approved posts, for admins and end users.
11 | * Renaming "digest" view to "singleday".
12 | * Make sure only valid properties can be added to posts and comments.
13 | * Added newsletter time setting (thanks @anthonymayer!).
14 | * Change "sign up" to "register" (thanks @Kikobeats!).
--------------------------------------------------------------------------------
/packages/telescope-rss/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-rss/.npm/package/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules
2 |
--------------------------------------------------------------------------------
/packages/telescope-rss/.npm/package/README:
--------------------------------------------------------------------------------
1 | This directory and the files immediately inside it are automatically generated
2 | when you change this package's NPM dependencies. Commit the files in this
3 | directory (npm-shrinkwrap.json, .gitignore, and this README) to source control
4 | so that others run the same versions of sub-dependencies.
5 |
6 | You should NOT check in the node_modules directory that Meteor automatically
7 | creates; if you are using git, the .gitignore file tells git to ignore it.
8 |
--------------------------------------------------------------------------------
/packages/telescope-rss/.npm/package/npm-shrinkwrap.json:
--------------------------------------------------------------------------------
1 | {
2 | "dependencies": {
3 | "rss": {
4 | "version": "0.3.2",
5 | "dependencies": {
6 | "xml": {
7 | "version": "0.0.12"
8 | },
9 | "mime": {
10 | "version": "1.2.11"
11 | }
12 | }
13 | }
14 | }
15 | }
16 |
--------------------------------------------------------------------------------
/packages/telescope-rss/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({summary: "Telescope RSS package"});
2 |
3 | Npm.depends({rss: "0.3.2"});
4 |
5 | Package.onUse(function (api) {
6 |
7 | api.use(['telescope-base', 'telescope-lib'], ['server']);
8 |
9 | api.add_files(['lib/server/rss.js', 'lib/server/routes.js'], ['server']);
10 |
11 | api.export(['serveRSS']);
12 | });
--------------------------------------------------------------------------------
/packages/telescope-search/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-search/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "load_more": "Mehr Laden",
3 | "search": "Suchen"
4 | }
--------------------------------------------------------------------------------
/packages/telescope-search/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "load_more": "Load more",
3 | "search": "Search",
4 | "search_logs": "Search Logs",
5 | "see_what_people_are_searching_for": "See what people are searching for."
6 | }
--------------------------------------------------------------------------------
/packages/telescope-search/i18n/es.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "load_more": "Cargar más",
3 | "search": "Búsqueda"
4 | }
--------------------------------------------------------------------------------
/packages/telescope-search/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "load_more": "Charger plus",
3 | "search": "Rechercher"
4 | }
--------------------------------------------------------------------------------
/packages/telescope-search/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "load_more": "Carica altro",
3 | "search": "Ricerca"
4 | }
--------------------------------------------------------------------------------
/packages/telescope-search/i18n/tr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "load_more": "Daha Fazla yükle",
3 | "search": "Search"
4 | }
--------------------------------------------------------------------------------
/packages/telescope-search/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "load_more": "加载更多",
3 | "search": "Search"
4 | }
--------------------------------------------------------------------------------
/packages/telescope-search/lib/client/css/search.css:
--------------------------------------------------------------------------------
1 | .mobile-nav .search{
2 | padding: 10px;
3 | }
4 | .search-field{
5 | color: #4a4444;
6 | border: 1px solid rgba(0,0,0,0.2);
7 | }
--------------------------------------------------------------------------------
/packages/telescope-search/lib/client/routes.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | PostsSearchController = PostsListController.extend({
4 | view: 'search',
5 | onBeforeAction: function() {
6 | var query = this.params.query;
7 | if ('q' in query) {
8 | Session.set('searchQuery', query.q);
9 | if (query.q) {
10 | Meteor.call('logSearch', query.q)
11 | }
12 | }
13 | this.next();
14 | }
15 | });
16 |
17 | Router.onBeforeAction(Router._filters.isAdmin, {only: ['logs']});
18 |
19 | // Search
20 |
21 | Router.route('/search/:limit?', {
22 | name: 'search',
23 | controller: PostsSearchController
24 | });
25 |
26 | // Search Logs
27 |
28 | Router.route('/logs/:limit?', {
29 | name: 'searchLogs',
30 | waitOn: function () {
31 | var limit = this.params.limit || 100;
32 | if(Meteor.isClient) {
33 | Session.set('logsLimit', limit);
34 | }
35 | return Meteor.subscribe('searches', limit);
36 | },
37 | data: function () {
38 | return Searches.find({}, {sort: {timestamp: -1}});
39 | },
40 | fastRender: true
41 | });
42 |
43 | });
44 |
--------------------------------------------------------------------------------
/packages/telescope-search/lib/client/views/search.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if canSearch}}
3 |
6 | {{/if}}
7 |
--------------------------------------------------------------------------------
/packages/telescope-search/lib/client/views/search_logs.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
Search Logs
4 |
5 |
6 |
7 | Keyword
8 | Timestamp
9 |
10 |
11 |
12 | {{#each this}}
13 | {{#if isNewDate}}
14 |
20 | {{/if}}
21 |
22 | {{keyword}}
23 | {{getTime}}
24 |
25 | {{/each}}
26 |
27 |
28 |
31 |
32 |
33 |
--------------------------------------------------------------------------------
/packages/telescope-search/lib/client/views/search_logs.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('searchLogs')].helpers({
3 | getTime: function () {
4 | return moment(this.timestamp).format("HH:mm:ss");
5 | },
6 | getDate: function () {
7 | currentDate = moment(this.timestamp).format("MMMM DD");
8 | return currentDate;
9 | },
10 | searchCount: function () {
11 | // TODO: doesn't work properly with "load more"
12 | var after = moment(this.timestamp).startOf('day').valueOf(),
13 | before = moment(this.timestamp).endOf('day').valueOf();
14 |
15 | return Searches.find({
16 | timestamp: {
17 | $gte: after,
18 | $lt: before
19 | }
20 | }).count();
21 | },
22 | isNewDate: function () {
23 | return (typeof currentDate === 'undefined') ? true : (currentDate !== moment(this.timestamp).format("MMMM DD"));
24 | },
25 | loadMoreUrl: function() {
26 | var count = parseInt(Session.get('logsLimit')) + 100;
27 | return '/logs/' + count;
28 | },
29 | });
30 | });
--------------------------------------------------------------------------------
/packages/telescope-search/lib/server/log_search.js:
--------------------------------------------------------------------------------
1 | var logSearch = function (keyword) {
2 | Searches.insert({
3 | timestamp: new Date(),
4 | keyword: keyword
5 | });
6 | };
7 |
8 | Meteor.methods({
9 | logSearch: function (keyword) {
10 | logSearch.call(this, keyword);
11 | }
12 | });
--------------------------------------------------------------------------------
/packages/telescope-search/lib/server/publications.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('searches', function(limit) {
2 | var limit = typeof limit === undefined ? 20 : limit;
3 | if(isAdminById(this.userId)){
4 | return Searches.find({}, {limit: limit, sort: {timestamp: -1}});
5 | }
6 | return [];
7 | });
--------------------------------------------------------------------------------
/packages/telescope-search/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-search/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({summary: "Telescope search package"});
2 |
3 | Package.onUse(function (api) {
4 |
5 | api.use(['telescope-lib', 'telescope-base', 'aldeed:simple-schema'], ['client', 'server']);
6 |
7 | api.use([
8 | 'jquery',
9 | 'underscore',
10 | 'iron:router',
11 | 'templating',
12 | 'tap:i18n'
13 | ], 'client');
14 |
15 | api.add_files([
16 | 'lib/search.js',
17 | 'package-tap.i18n'
18 | ], ['client', 'server']);
19 |
20 | api.add_files([
21 | 'lib/client/routes.js',
22 | 'lib/client/views/search.html',
23 | 'lib/client/views/search.js',
24 | 'lib/client/css/search.css',
25 | 'lib/client/views/search_logs.html',
26 | 'lib/client/views/search_logs.js'
27 | ], ['client']);
28 |
29 | api.add_files([
30 | 'lib/server/log_search.js',
31 | 'lib/server/publications.js'
32 | ], ['server']);
33 |
34 | api.add_files([
35 | "i18n/de.i18n.json",
36 | "i18n/en.i18n.json",
37 | "i18n/es.i18n.json",
38 | "i18n/fr.i18n.json",
39 | "i18n/it.i18n.json",
40 | "i18n/zh-CN.i18n.json",
41 | ], ["client", "server"]);
42 |
43 | api.export(['adminMenu', 'viewParameters']);
44 | });
--------------------------------------------------------------------------------
/packages/telescope-singleday/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-singleday/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "the_top_5_posts_of_each_day": "Die Top-5-Links eines jeden Tages.",
3 | "previous_day": "Einen Tag zurück",
4 | "next_day": "Einen Tag vor",
5 | "sorry_no_posts_for_today": "Heute gibt es keine Links.",
6 | "sorry_no_posts_for": "Keine Links für",
7 | "today": "Heute",
8 | "yesterday": "Gestern"
9 | }
--------------------------------------------------------------------------------
/packages/telescope-singleday/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "the_top_5_posts_of_each_day": "The top 5 posts of each day.",
3 | "previous_day": "Previous Day",
4 | "next_day": "Next Day",
5 | "sorry_no_posts_for_today": "Sorry, no posts for today",
6 | "sorry_no_posts_for": "Sorry, no posts for",
7 | "today": "Today",
8 | "yesterday": "Yesterday",
9 | "single_day": "Single Day",
10 | "posts_of_a_single_day": "The posts of a single day."
11 | }
--------------------------------------------------------------------------------
/packages/telescope-singleday/i18n/es.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "the_top_5_posts_of_each_day": "Los 5 mejores posts de cada día",
3 | "previous_day": "Dia anterior",
4 | "next_day": "Dia siguiente",
5 | "sorry_no_posts_for_today": "Lo sentimos, no hay post para hoy",
6 | "today": "Hoy",
7 | "yesterday": "Ayer"
8 | }
--------------------------------------------------------------------------------
/packages/telescope-singleday/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "the_top_5_posts_of_each_day": "5 meilleurs post par jours",
3 | "previous_day": "Jour précédent",
4 | "next_day": "Jour suivant",
5 | "sorry_no_posts_for_today": "Désolé, aucun post aujourd'hui",
6 | "sorry_no_posts_for": "Désolé, aucun post pour",
7 | "today": "Aujourd'hui",
8 | "yesterday": "Hier"
9 | }
--------------------------------------------------------------------------------
/packages/telescope-singleday/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "the_top_5_posts_of_each_day": "I 5 migliori post di ogni giorno.",
3 | "previous_day": "Giorno Precedente",
4 | "next_day": "Giorno Successivo",
5 | "sorry_no_posts_for_today": "Ci spiace, non ci sono post per oggi",
6 | "sorry_no_posts_for": "Ci spiace, non ci sono post per",
7 | "today": "Oggi",
8 | "yesterday": "Ieri"
9 | }
--------------------------------------------------------------------------------
/packages/telescope-singleday/i18n/tr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "the_top_5_posts_of_each_day": "Her günün en üst 5 paylaşımı",
3 | "previous_day": "Önceki gün",
4 | "next_day": "Sonraki gün",
5 | "Sorry, no posts for today": "Özür dileriz, bugün bir paylaşım yok",
6 | "sorry_no_posts_for_today": "Özür dileriz, paylaşım yok",
7 | "today": "Bugün",
8 | "yesterday": "Dün"
9 | }
--------------------------------------------------------------------------------
/packages/telescope-singleday/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "the_top_5_posts_of_each_day": "每天前5名的帖子",
3 | "previous_day": "前一天",
4 | "next_day": "后一天",
5 | "sorry_no_posts_for_today": "抱歉今天没有新的帖子",
6 | "today": "今天",
7 | "yesterday": "昨天"
8 | }
--------------------------------------------------------------------------------
/packages/telescope-singleday/lib/client/templates/single_day.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if showDateNav}}
3 | {{> Template.dynamic template=singleDayNav}}
4 | {{/if}}
5 | {{> Template.dynamic template=posts_list data=context}}
6 |
7 |
--------------------------------------------------------------------------------
/packages/telescope-singleday/lib/client/templates/single_day_nav.html:
--------------------------------------------------------------------------------
1 |
2 |
13 |
14 |
--------------------------------------------------------------------------------
/packages/telescope-singleday/lib/routes.js:
--------------------------------------------------------------------------------
1 | // Controller for post digest
2 |
3 | PostsSingleDayController = RouteController.extend({
4 |
5 | template: getTemplate('singleDay'),
6 |
7 | data: function() {
8 | var currentDate = this.params.day ? new Date(this.params.year, this.params.month-1, this.params.day) : Session.get('today');
9 | Session.set('currentDate', currentDate);
10 | },
11 |
12 | getTitle: function () {
13 | return i18n.t('single_day') + ' - ' + getSetting('title', 'Telescope');
14 | },
15 |
16 | getDescription: function () {
17 | return i18n.t('posts_of_a_single_day');
18 | },
19 |
20 | fastRender: true
21 |
22 | });
23 |
24 | Meteor.startup(function () {
25 |
26 | // Digest
27 |
28 | Router.route('/day/:year/:month/:day', {
29 | name: 'postsSingleDay',
30 | controller: PostsSingleDayController
31 | });
32 |
33 | Router.route('/day', {
34 | name: 'postsSingleDayDefault',
35 | controller: PostsSingleDayController
36 | });
37 |
38 | });
--------------------------------------------------------------------------------
/packages/telescope-singleday/lib/singleday.js:
--------------------------------------------------------------------------------
1 | viewsMenu.push({
2 | route: 'postsSingleDayDefault',
3 | label: 'digest',
4 | description: 'posts_of_a_single_day'
5 | });
6 |
7 | viewParameters.singleday = function (terms) {
8 | return {
9 | find: {
10 | postedAt: {
11 | $gte: terms.after,
12 | $lt: terms.before
13 | }
14 | },
15 | options: {
16 | sort: {sticky: -1, score: -1}
17 | }
18 | };
19 | };
20 |
21 | getDateURL = function(moment){
22 | return Router.path('postsSingleDay', {
23 | year: moment.year(),
24 | month: moment.month() + 1,
25 | day: moment.date()
26 | });
27 | };
--------------------------------------------------------------------------------
/packages/telescope-singleday/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-subscribe-to-posts/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-subscribe-to-posts/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "subscribed_posts": "Subscribed Posts",
3 | "subscribe_to_thread": "Subscribe to comment thread",
4 | "unsubscribe_from_thread": "Unsubscribe from comment thread"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-subscribe-to-posts/lib/client/stylesheets/subscribe-to-posts.scss:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/packages/telescope-subscribe-to-posts/lib/client/stylesheets/subscribe-to-posts.scss
--------------------------------------------------------------------------------
/packages/telescope-subscribe-to-posts/lib/client/templates/post_subscribe.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if canSubscribe}}
3 |
14 | {{/if}}
15 |
16 |
--------------------------------------------------------------------------------
/packages/telescope-subscribe-to-posts/lib/client/templates/user_subscribed_posts.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
{{_ "subscribed_posts"}}
4 |
5 |
6 |
7 | Post
8 | Subscribed At
9 |
10 |
11 | {{#each posts}}
12 |
13 | {{title}}
14 | {{formatDate subscribedAt "MM/DD/YYYY, HH:mm"}}
15 |
16 | {{/each}}
17 | {{#if hasMorePosts}}
18 |
19 |
20 | {{_ "load_more"}}
21 |
22 |
23 | {{/if}}
24 |
25 |
26 |
27 |
--------------------------------------------------------------------------------
/packages/telescope-subscribe-to-posts/lib/server/publications.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('userSubscribedPosts', function(terms) {
2 | var parameters = getPostsParameters(terms);
3 | var posts = Posts.find(parameters.find, parameters.options);
4 | return posts;
5 | });
6 |
--------------------------------------------------------------------------------
/packages/telescope-subscribe-to-posts/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-tags/i18n/de.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "categories": "Kategorien"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/i18n/en.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "categories": "Categories",
3 | "add_and_remove_categories": "Add and remove categories."
4 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/i18n/es.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "categories": "Categorías"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/i18n/fr.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "categories": "Catégories"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/i18n/it.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "categories": "Categorie"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/i18n/zh-CN.i18n.json:
--------------------------------------------------------------------------------
1 | {
2 | "categories": "分类"
3 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/routes.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 |
3 | Router.onBeforeAction(Router._filters.isAdmin, {only: ['categories']});
4 |
5 | PostsCategoryController = PostsListController.extend({
6 |
7 | view: 'category',
8 |
9 | getCurrentCategory: function () {
10 | return Categories.findOne({slug: this.params.slug});
11 | },
12 |
13 | getTitle: function () {
14 | var category = this.getCurrentCategory();
15 | return category.name + ' - ' + getSetting('title', 'Telescope');
16 | },
17 |
18 | getDescription: function () {
19 | return this.getCurrentCategory().description;
20 | }
21 |
22 | });
23 |
24 | // Categories
25 |
26 | Router.route('/category/:slug/:limit?', {
27 | name: 'posts_category',
28 | controller: PostsCategoryController,
29 | onAfterAction: function() {
30 | this.slug = this.params.slug;
31 | Session.set('categorySlug', this.params.slug);
32 | }
33 | });
34 |
35 | // Categories Admin
36 |
37 | Router.route('/categories', {
38 | name: 'categories'
39 | });
40 |
41 |
42 | });
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/scss/categories.scss:
--------------------------------------------------------------------------------
1 | $red: #DD3416;
2 | $light-yellow:#fffcea;
3 |
4 | .post-category{
5 | display:inline-block;
6 | font-size:12px;
7 | background:#eee;
8 | padding:3px 5px 1px 5px;
9 | text-transform:uppercase;
10 | font-weight:normal;
11 | vertical-align:middle;
12 | &:hover{
13 | background:$red;
14 | color:white;
15 | }
16 | }
17 |
18 | .add-category{
19 | background: $light-yellow;
20 | }
21 |
22 | .post-categories{
23 | text-align: right;
24 | }
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/categories.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
Add new category:
4 | {{> quickForm collection="Categories" id="insertCategoryForm" type="insert" label-class="control-label" input-col-class="controls" template="telescope"}}
5 |
6 | {{#each categories}}
7 | {{> UI.dynamic template=categoryItem}}
8 | {{/each}}
9 |
10 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/categories.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('categories')].helpers({
3 | categories: function(){
4 | return Categories.find({}, {sort: {order: 1, name: 1}});
5 | },
6 | categoryItem: function () {
7 | return getTemplate('categoryItem');
8 | }
9 | });
10 |
11 | Template[getTemplate('categories')].events({
12 | 'click input[type=submit]': function(e){
13 | e.preventDefault();
14 |
15 | var name = $('#name').val();
16 | var numberOfCategories = Categories.find().count();
17 | var order = parseInt($('#order').val()) || (numberOfCategories + 1);
18 | var slug = slugify(name);
19 |
20 | Meteor.call('submitCategory', {
21 | name: name,
22 | order: order,
23 | slug: slug
24 | }, function(error, categoryName) {
25 | if(error){
26 | console.log(error);
27 | flashMessage(error.reason, "error");
28 | clearSeenMessages();
29 | }else{
30 | $('#name').val('');
31 | // flashMessage('New category "'+categoryName+'" created', "success");
32 | }
33 | });
34 | }
35 | });
36 | });
37 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/categories_menu.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if hasCategories}}
3 |
18 | {{/if}}
19 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/categories_menu.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('categoriesMenu')].helpers({
3 | hasCategories: function(){
4 | return typeof Categories !== 'undefined' && Categories.find().count();
5 | },
6 | cat: function () {
7 | return __('categories')
8 | },
9 | categories: function(){
10 | return Categories.find({}, {sort: {order: 1, name: 1}});
11 | },
12 | categoryLink: function () {
13 | return getCategoryUrl(this.slug);
14 | }
15 | });
16 | });
17 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/category_item.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | {{> quickForm collection="Categories" id=formId type="update" doc=this label-class="control-label" input-col-class="controls" template="telescope"}}
4 |
Delete
5 |
6 |
7 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/category_item.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('categoryItem')].helpers({
3 | formId: function () {
4 | return 'updateCategory-'+ this._id
5 | }
6 | });
7 |
8 | Template[getTemplate('categoryItem')].events({
9 | 'click .delete-link': function(e, instance){
10 | e.preventDefault();
11 | if (confirm("Delete category?")) {
12 | Categories.remove(instance.data._id);
13 | }
14 | }
15 | });
16 | });
17 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/post_categories.html:
--------------------------------------------------------------------------------
1 |
2 | {{#each categoriesArray}}
3 | {{name}}
4 | {{/each}}
5 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/client/templates/post_categories.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | Template[getTemplate('postCategories')].helpers({
3 | categoriesArray: function(){
4 | return _.map(this.categories, function (categoryId) { // note: this.categories maybe be undefined
5 | return Categories.findOne(categoryId);
6 | });
7 | },
8 | categoryLink: function(){
9 | return getCategoryUrl(this.slug);
10 | }
11 | });
12 | });
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/custom_fields.js:
--------------------------------------------------------------------------------
1 | addToPostSchema.push(
2 | {
3 | propertyName: 'categories',
4 | propertySchema: {
5 | type: [String],
6 | optional: true,
7 | editable: true,
8 | autoform: {
9 | editable: true,
10 | noselect: true,
11 | options: function () {
12 | var categories = Categories.find().map(function (category) {
13 | return {
14 | value: category._id,
15 | label: category.name
16 | }
17 | });
18 | return categories;
19 | }
20 | }
21 | }
22 | }
23 | );
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/hooks.js:
--------------------------------------------------------------------------------
1 | adminMenu.push({
2 | route: 'categories',
3 | label: 'Categories',
4 | description: 'add_and_remove_categories'
5 | });
6 |
7 | // push "categories" modules to postHeading
8 | postHeading.push({
9 | template: 'postCategories',
10 | order: 30
11 | });
12 |
13 | // push "categoriesMenu" template to primaryNav
14 | primaryNav.push({
15 | template: 'categoriesMenu',
16 | order: 50
17 | });
18 |
19 | // we want to wait until categories are all loaded to load the rest of the app
20 | preloadSubscriptions.push('categories');
21 |
--------------------------------------------------------------------------------
/packages/telescope-tags/lib/server/publications.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('categories', function() {
2 | if(can.viewById(this.userId)){
3 | return Categories.find();
4 | }
5 | return [];
6 | });
--------------------------------------------------------------------------------
/packages/telescope-tags/package-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "translation_function_name": "__",
3 | "helper_name": "_",
4 | "namespace": "project"
5 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/global/_links.scss:
--------------------------------------------------------------------------------
1 | a{
2 | text-decoration: none;
3 | &, &:link, &:visited, &:active{
4 | color: $text;
5 | font-weight: bold;
6 | }
7 | &:hover{
8 | color: $red;
9 | }
10 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/global/_main.scss:
--------------------------------------------------------------------------------
1 | .hidden{
2 | display:none;
3 | }
4 | .visible{
5 | display: block;
6 | }
7 | .overlay{
8 | position:fixed;
9 | top:0;
10 | left:0;
11 | height:100%;
12 | width:100%;
13 | z-index:50;
14 | }
15 |
16 | #spinner{
17 | margin: 100px 0;
18 | }
19 | .debug{
20 | display:none;
21 | }
22 |
23 | .footer{
24 | text-align:center;
25 | padding:10px 0 70px 0;
26 | color:black(0.4);
27 | font-size:14px;
28 | &.absolute{
29 | position:absolute;
30 | }
31 | }
32 | #login-buttons .loading{
33 | display:none;
34 | }
35 | #loading, .loading-page{
36 | height:300px;
37 | }
38 |
39 | .notifications-toggle{
40 | background: white;
41 | margin-bottom: $grid-margin;
42 | padding: $grid-padding;
43 | }
44 |
45 | .search-date-header{
46 | background: $lightest-grey;
47 | th{
48 | @include cf;
49 | }
50 | .search-date{
51 | display: block;
52 | float: left;
53 | font-weight: bold;
54 | }
55 | .search-count{
56 | font-size: 13px;
57 | display: block;
58 | float: right;
59 | }
60 | }
61 |
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/global/_tables.scss:
--------------------------------------------------------------------------------
1 | table{
2 | width: 100%;
3 | tr{
4 | border-bottom: 1px solid #eee;
5 | td, th{
6 | padding:10px;
7 | vertical-align: middle;
8 | }
9 | }
10 | thead{
11 | tr{
12 | td, th{
13 | font-weight:bold;
14 | }
15 | }
16 | }
17 | tbody{
18 | tr{
19 | td{
20 |
21 | }
22 | }
23 | }
24 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/global/_typography.scss:
--------------------------------------------------------------------------------
1 | html, body, input, button{
2 | font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
3 | }
4 | h1,h2,h3,h4,h5, ul, ol, li, p, pre, div{
5 | line-height: 1.5;
6 | }
7 | h1{
8 | font-size: 40px;
9 | }
10 | h2{
11 | font-size: 30px;
12 | }
13 | h3{
14 | font-size: 20px;
15 | }
16 | h4{
17 | font-size: 16px;
18 | }
19 | li{
20 | margin: 0 0 10px 0;
21 | }
22 | .important{
23 | color: $red;
24 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/includes/_breakpoints.scss:
--------------------------------------------------------------------------------
1 | $grid-unit:70px;
2 | $grid-margin:10px;
3 | $grid-padding:15px;
4 | $break-small:500px;
5 |
6 | $small-break: 40em;
7 | $medium-break: 50em;
8 |
9 | @mixin small(){
10 | @media screen and (max-width: $small-break) {
11 | @content;
12 | }
13 | }
14 | @mixin small-medium(){
15 | @media screen and (max-width: $medium-break) {
16 | @content;
17 | }
18 | }
19 | @mixin medium(){
20 | @media screen and (min-width: $small-break) and (max-width: $medium-break) {
21 | @content;
22 | }
23 | }
24 | @mixin medium-large(){
25 | @media screen and (min-width: $small-break) {
26 | @content;
27 | }
28 | }
29 | @mixin large(){
30 | @media screen and (min-width: $medium-break) {
31 | @content;
32 | }
33 | }
34 |
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/includes/_colors.scss:
--------------------------------------------------------------------------------
1 | $red: #DD3416;
2 | $green:#a3d06d;
3 |
4 | $blue:#7ac0e4;
5 | $dark-blue:#4e555d;
6 | $blue-grey:#b3c1c6;
7 | $blue-grey2:#a4a9ab;
8 | $light-blue:#d8e9f5;
9 | $light-blue2:#92b5c3;
10 |
11 | $yellow:#f8e121;
12 | $light-yellow:#fffcea;
13 |
14 | $grey:#b5b0b0;
15 | $lighter-grey:#dfdbdb;
16 | $lightest-grey:#e7eff2;
17 | $dark-grey:#444444;
18 |
19 | $header-bg:$dark-grey;
20 | $text:$dark-grey;
21 | $medium-text:$blue-grey2;
22 | $light-text:$blue-grey;
23 | $lighter-text:$lighter-grey;
24 | $border-color:$grey;
25 | $highlight-color:$dark-blue;
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/screen.scss:
--------------------------------------------------------------------------------
1 | // Includes
2 |
3 | @import "includes/breakpoints";
4 | @import "includes/colors";
5 | @import "includes/mixins";
6 |
7 | // Global Styles (forms, typography, etc.)
8 |
9 | @import "global/forms";
10 | @import "global/links";
11 | @import "global/main";
12 | @import "global/markdown";
13 | @import "global/tables";
14 | @import "global/typography";
15 |
16 | // Specific Styles (header, posts, etc.)
17 |
18 | @import "specific/avatars";
19 | @import "specific/dropdown";
20 | @import "specific/errors";
21 | @import "specific/header";
22 | @import "specific/layout";
23 | @import "specific/loading";
24 | @import "specific/mobile_nav";
25 | @import "specific/notifications";
26 | @import "specific/posts";
27 | @import "specific/users";
28 |
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/specific/_avatars.scss:
--------------------------------------------------------------------------------
1 | .avatar-xsmall {
2 | .avatar-initials{
3 | font-size: 12px;
4 | line-height: 20px;
5 | }
6 | }
7 | .avatar-small {
8 | height: 24px;
9 | width: 24px;
10 | .avatar-initials{
11 | font-size: 13px;
12 | line-height: 24px;
13 | }
14 | }
15 | .avatar-medium {
16 | height: 30px;
17 | width: 30px;
18 | .avatar-initials{
19 | font-size: 14px;
20 | line-height: 30px;
21 | }
22 | }
23 |
24 | .avatar-initials{
25 | font-weight: normal;
26 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/specific/_errors.scss:
--------------------------------------------------------------------------------
1 | .error, .at-error{
2 | background: $red;
3 | color: white;
4 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/specific/_layout.scss:
--------------------------------------------------------------------------------
1 | *, *:before, *:after {
2 | box-sizing: border-box;
3 | line-height: 1.5;
4 | }
5 |
6 | html, body, .outer-wrapper{
7 | height:100%;
8 | }
9 |
10 | body{
11 | background:#eee;
12 | font-size: 14px;
13 | @include small{
14 | overflow-x: hidden;
15 | }
16 | }
17 |
18 | .outer-wrapper{
19 | position:relative;
20 | }
21 | .content-wrapper{
22 | padding-bottom:20px;
23 | }
24 | .content-wrapper{
25 | padding: 0 10px;
26 | max-width: 1000px;
27 | margin: 0 auto;
28 | @include small{
29 | overflow-x: hidden;
30 | overflow-y: hidden;
31 | }
32 | }
33 | .grid-module, .at-form{
34 | background: white;
35 | padding: $grid-padding;
36 | margin-bottom: $grid-margin;
37 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/specific/_loading.scss:
--------------------------------------------------------------------------------
1 | .loading-module{
2 | height: 70px;
3 | position: relative;
4 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/specific/_notifications.scss:
--------------------------------------------------------------------------------
1 | .notification-item{
2 | margin-bottom: 10px;
3 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/specific/_posts.scss:
--------------------------------------------------------------------------------
1 | .posts-wrapper{
2 | background: none;
3 | }
4 | .more-button{
5 | display: block;
6 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-base/lib/client/scss/specific/_users.scss:
--------------------------------------------------------------------------------
1 | .user-list, .user-table{
2 | font-size: 13px;
3 | .user{
4 | .user-avatar{
5 | height:30px;
6 | width:30px;
7 | background-size: 30px 30px;
8 | display:block;
9 | border-radius: 30px;
10 | }
11 | .posts-list{
12 |
13 | }
14 | }
15 | }
16 | .filter-sort{
17 | @include cf;
18 | padding: $grid-padding;
19 | background: black(0.05);
20 | a, span{
21 | display: inline-block;
22 | margin-right: 20px;
23 | &.active{
24 | border-bottom: 2px solid $blue;
25 | }
26 | &:last-child{
27 | margin-right: 0;
28 | }
29 | }
30 | .filter{
31 | float: left;
32 | }
33 | .sort{
34 | float: right;
35 | }
36 |
37 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
3 | config.codekit
4 | lib/client/config.codekit
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/modules/_accounts.scss:
--------------------------------------------------------------------------------
1 | .at-oauth{
2 | text-align: center;
3 | .at-social-btn{
4 | margin: 0 auto 15px auto;
5 | }
6 | }
7 |
8 | .at-sep{
9 | text-align: center;
10 | position: relative;
11 | overflow: hidden;
12 | margin-bottom: 15px;
13 | &:before, &:after{
14 | display: block;
15 | content: " ";
16 | border-bottom: 1px solid #ddd;
17 | width: 100%;
18 | position: absolute;
19 | top: 48%;
20 | }
21 | &:before{
22 | left: -55%;
23 | }
24 | &:after{
25 | right: -55%;
26 | }
27 | }
28 |
29 | .at-input{
30 | label{
31 | margin-bottom: 5px;
32 | }
33 | }
34 |
35 | #at-forgotPwd{
36 | font-size: 13px;
37 | float: right;
38 | margin-top: -8px;
39 | }
40 |
41 | #at-btn{
42 | margin: 0 auto;
43 | }
44 | .at-title{
45 | border-bottom: 1px solid #ddd;
46 | margin-bottom: 20px;
47 | padding-bottom: 5px;
48 | text-align: center;
49 | }
50 | .at-signup-link, .at-signin-link{
51 | border-top: 1px solid #ddd;
52 | margin-top: 15px;
53 | padding-top: 15px;
54 | text-align: center;
55 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/modules/_banners.scss:
--------------------------------------------------------------------------------
1 | .banner.banner{
2 | background: rgba(255,255,255,0.7);
3 | margin-bottom: 10px;
4 | padding: 20px;
5 | position: relative;
6 | overflow: hidden;
7 | }
8 |
9 | .banner-heading{
10 | border-bottom: 1px solid $grey;
11 | font-weight: bold;
12 | color: $medium-text;
13 | padding-bottom: 10px;
14 | margin-bottom: 10px;
15 | }
16 |
17 | .banner-dismiss, .banner-dismiss:link, .banner-dismiss:visited{
18 | display: block;
19 | position: absolute;
20 | height: 30px;
21 | width: 30px;
22 | border-radius: 100%;
23 | background: rgba(0,0,0,0.15);
24 | color: white;
25 | top: 50%;
26 | margin-top: -15px;
27 | right: 20px;
28 | font-size: 24px;
29 | text-align: center;
30 | vertical-align: middle;
31 | line-height: 32px;
32 | @include small{
33 | top: 10px;
34 | right: 10px;
35 | margin-top: 0px;
36 | }
37 | }
38 | .banner-dismiss:hover{
39 | color: inherit;
40 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/modules/_dialogs.scss:
--------------------------------------------------------------------------------
1 | .dialog{
2 | h2{
3 | text-align:center;
4 | padding-bottom:$grid-padding;
5 | margin-bottom:$grid-margin;
6 | }
7 | margin-bottom:$grid-margin;
8 | }
9 | .footer-notice{
10 | text-align:center;
11 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/modules/_errors.scss:
--------------------------------------------------------------------------------
1 | .error, .at-error{
2 | @extend .grid-block;
3 | margin-bottom:$grid-margin;
4 | text-align:center;
5 | background:$red;
6 | color:white;
7 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/modules/_icons.scss:
--------------------------------------------------------------------------------
1 | .action-icon{
2 | font-size: 30px;
3 | height: 30px;
4 | display: block;
5 | &:before{
6 | position: relative;
7 | top: -10px;
8 | }
9 | }
10 | .action-label{
11 | font-weight: bold;
12 | display:block;
13 | height:20px;
14 | line-height:20px;
15 | bottom:5px;
16 | left:0px;
17 | font-size:13px;
18 | color:$light-text;
19 | pointer-events:none;
20 | // color:$red;
21 | }
22 | .action-count{
23 | position:absolute;
24 | top:4px;
25 | display:block;
26 | width:100%;
27 | height:11px;
28 | line-height:11px;
29 | font-size:14px;
30 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/modules/_user-profile.scss:
--------------------------------------------------------------------------------
1 | .user-profile {
2 | .user-avatar {
3 | height: 80px;
4 | width: 80px;
5 | display: block;
6 | border-radius: 80px;
7 | }
8 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/partials/_colors.scss:
--------------------------------------------------------------------------------
1 | $red: #DD3416;
2 | $green:#a3d06d;
3 |
4 | $blue:#7ac0e4;
5 | $dark-blue:#4e555d;
6 | $blue-grey:#b3c1c6;
7 | $blue-grey2:#a4a9ab;
8 | $light-blue:#d8e9f5;
9 | $light-blue2:#92b5c3;
10 |
11 | $yellow:#f8e121;
12 | $light-yellow:#fffce0;
13 |
14 | $grey:#b5b0b0;
15 | $lighter-grey:#dfdbdb;
16 | $lightest-grey:#e7eff2;
17 | $dark-grey:#4a4444;
18 |
19 | $header-bg:$dark-grey;
20 | $text:$dark-grey;
21 | $medium-text:$blue-grey2;
22 | $light-text:$blue-grey;
23 | $lighter-text:$lighter-grey;
24 | $border-color:$grey;
25 | $highlight-color:$dark-blue;
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/partials/_grid.scss:
--------------------------------------------------------------------------------
1 | $grid-unit:70px;
2 | $grid-margin:10px;
3 | $grid-padding:15px;
4 | $break-small:500px;
5 |
6 | $small-break: 30em;
7 | $medium-break: 50em;
8 |
9 | @mixin small(){
10 | @media screen and (max-width: $small-break) {
11 | @content;
12 | }
13 | }
14 | @mixin small-medium(){
15 | @media screen and (max-width: $medium-break) {
16 | @content;
17 | }
18 | }
19 | @mixin medium(){
20 | @media screen and (min-width: $small-break) and (max-width: $medium-break) {
21 | @content;
22 | }
23 | }
24 | @mixin medium-large(){
25 | @media screen and (min-width: $small-break) {
26 | @content;
27 | }
28 | }
29 | @mixin large(){
30 | @media screen and (min-width: $medium-break) {
31 | @content;
32 | }
33 | }
34 |
35 | .content-wrapper{
36 | padding: 0 10px;
37 | @include small{
38 | overflow-x: hidden;
39 | }
40 | }
41 | .grid{
42 | width:100%;
43 | max-width: 1000px;
44 | margin-left: auto;
45 | margin-right: auto;
46 | }
47 | .grid-small, .at-form{
48 | width: 100%;
49 | @include medium-large{
50 | max-width:500px;
51 | }
52 | margin-left: auto;
53 | margin-right: auto;
54 | }
55 |
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/partials/_tooltips.scss:
--------------------------------------------------------------------------------
1 | .has-tooltip{
2 | position:relative;
3 | .tooltip{
4 | pointer-events: none;
5 | position:absolute;
6 | z-index:9999;
7 | left:50%;
8 | top:-40px;
9 | opacity:0;
10 | transition: ease-out, opacity, 300ms, 0ms;
11 | span{
12 | display:block;
13 | white-space:nowrap;
14 | position:relative;
15 | background:black(0.6);
16 | border-radius: 3px;
17 | padding:0px 8px;
18 | left:-50%;
19 | font-size:14px;
20 | color:#fff;
21 | &:after {
22 | top: 100%;
23 | border: solid transparent;
24 | content: " ";
25 | height: 0;
26 | width: 0;
27 | position: absolute;
28 | border-top-color: black(0.6);
29 | border-width: 6px;
30 | left: 50%;
31 | margin-left: -6px;
32 | }
33 | }
34 | }
35 | &:hover .tooltip{
36 | opacity:1;
37 | }
38 | }
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/partials/_typography.scss:
--------------------------------------------------------------------------------
1 | @import url(https://fonts.googleapis.com/css?family=Source+Sans+Pro:400,700,400italic,700italic);
2 |
3 | body, textarea, input, button, input[type="submit"], input[type="button"]{
4 | font-family:"Source Sans Pro", "Helvetica Neue", Helvetica, sans-serif;
5 | }
6 | body, textarea, input{
7 | color:$text;
8 | line-height:1.6;
9 | }
10 | .post-title, .header, .post-rank, .button{
11 | // font-family:"kulturista-web", Rokkitt, Georgia, serif;
12 | }
13 | h2{
14 | font-size: 36px;
15 | margin-bottom: 10px;
16 | }
17 | h3{
18 | font-weight:bold;
19 | margin-bottom:10px;
20 | }
21 | .small{
22 | font-size: 80%;
23 | color:$light-text;
24 | }
25 | strong{
26 | font-weight: bold;
27 | }
28 | em{
29 | font-style: italic;
30 | }
31 |
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/client/scss/screen.scss:
--------------------------------------------------------------------------------
1 |
2 | @import "partials/grid";
3 | @import "partials/colors";
4 | @import "partials/mixins";
5 | @import "partials/typography";
6 | @import "partials/icons";
7 | @import "partials/tooltips";
8 |
9 | @import "modules/accounts";
10 | @import "modules/banners";
11 | @import "modules/nav";
12 | @import "modules/posts";
13 | @import "modules/comments";
14 | @import "modules/dialogs";
15 | @import "modules/user-profile";
16 | @import "modules/errors";
17 | @import "modules/icons";
--------------------------------------------------------------------------------
/packages/telescope-theme-hubble/lib/hubble.js:
--------------------------------------------------------------------------------
1 | themeSettings.useDropdowns = true; // not strictly needed since "true" is the current default
--------------------------------------------------------------------------------
/packages/telescope-update-prompt/.gitignore:
--------------------------------------------------------------------------------
1 | .build*
2 |
--------------------------------------------------------------------------------
/packages/telescope-update-prompt/lib/client/templates/update_banner.css:
--------------------------------------------------------------------------------
1 | .update-banner{
2 | overflow: hidden;
3 | }
4 | .update-content{
5 | float: left;
6 | }
7 | .update-version{
8 | float: left;
9 | background: #DD3416;
10 | color: white;
11 | text-align: center;
12 | padding: 5px 10px;
13 | margin: 0px 15px 0px 0px;
14 | }
15 | .update-prompt{
16 | font-weight: bold;
17 | line-height: 1;
18 | margin-bottom: 5px;
19 | }
20 | .update-message{
21 | font-size: 14px;
22 | }
--------------------------------------------------------------------------------
/packages/telescope-update-prompt/lib/client/templates/update_banner.html:
--------------------------------------------------------------------------------
1 |
2 | {{#if showBanner}}
3 |
4 |
{{version}}
5 |
6 |
A new version of Telescope is available.
7 |
8 | You have: {{currentVersion}}. Note: this message is only displayed to admins.
9 | View changelog |
10 | View update instructions
11 |
12 |
13 |
14 | {{/if}}
15 |
--------------------------------------------------------------------------------
/packages/telescope-update-prompt/lib/client/templates/update_banner.js:
--------------------------------------------------------------------------------
1 | Template[getTemplate('updateBanner')].helpers({
2 | showBanner: function () {
3 | return Session.get('updateVersion');
4 | },
5 | version: function () {
6 | return Session.get('updateVersion');
7 | },
8 | currentVersion: function () {
9 | return telescopeVersion;
10 | },
11 | message: function () {
12 | return Session.get('updateMessage');
13 | }
14 | });
--------------------------------------------------------------------------------
/packages/telescope-update-prompt/lib/server/phone_home.js:
--------------------------------------------------------------------------------
1 | Meteor.methods({
2 | phoneHome: function () {
3 |
4 | return false;
5 | }
6 | })
7 |
--------------------------------------------------------------------------------
/packages/telescope-update-prompt/package.js:
--------------------------------------------------------------------------------
1 | Package.describe({
2 | summary: "Telescope update prompt package.",
3 | version: '0.1.0',
4 | name: "telescope-update-prompt"
5 | });
6 |
7 | Package.onUse(function (api) {
8 |
9 | api.use(['telescope-lib', 'telescope-base', 'http'], ['client', 'server']);
10 |
11 | api.use([
12 | 'jquery',
13 | 'underscore',
14 | 'iron:router',
15 | 'templating'
16 | ], 'client');
17 |
18 |
19 | api.add_files([
20 | 'lib/client/update.js',
21 | 'lib/client/templates/update_banner.html',
22 | 'lib/client/templates/update_banner.js',
23 | 'lib/client/templates/update_banner.css'
24 | ], ['client']);
25 |
26 | api.add_files([
27 | 'lib/server/phone_home.js'
28 | ], ['server']);
29 |
30 | api.export([
31 | 'compareVersions'
32 | ]);
33 | });
--------------------------------------------------------------------------------
/project-tap.i18n:
--------------------------------------------------------------------------------
1 | {
2 | "helper_name": "_"
3 | }
4 |
--------------------------------------------------------------------------------
/public/img/bg-black.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/bg-black.png
--------------------------------------------------------------------------------
/public/img/bg-black@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/bg-black@2x.png
--------------------------------------------------------------------------------
/public/img/bg-header.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/bg-header.png
--------------------------------------------------------------------------------
/public/img/bg-header@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/bg-header@2x.png
--------------------------------------------------------------------------------
/public/img/bg.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/bg.png
--------------------------------------------------------------------------------
/public/img/bg@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/bg@2x.png
--------------------------------------------------------------------------------
/public/img/default-avatar.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/default-avatar.png
--------------------------------------------------------------------------------
/public/img/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/favicon.ico
--------------------------------------------------------------------------------
/public/img/loading.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/loading.gif
--------------------------------------------------------------------------------
/public/img/logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/logo.png
--------------------------------------------------------------------------------
/public/img/logo@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/logo@2x.png
--------------------------------------------------------------------------------
/public/img/telescope-logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/telescope-logo.png
--------------------------------------------------------------------------------
/public/img/telescope-logo2.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/telescope-logo2.png
--------------------------------------------------------------------------------
/public/img/telescope-logo@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jparyani/Telescope/a291d716a16595d127f66f5064f4ae1a761051dd/public/img/telescope-logo@2x.png
--------------------------------------------------------------------------------
/scss.json:
--------------------------------------------------------------------------------
1 | {
2 | "enableAutoprefixer": true,
3 | "outputStyle": "compressed",
4 | "sourceComments": true,
5 | "sourceMap": true
6 | }
--------------------------------------------------------------------------------
/server/publications/posts_list.js:
--------------------------------------------------------------------------------
1 | // Publish a list of posts
2 |
3 | Meteor.publish('postsList', function(terms) {
4 | if(can.viewById(this.userId)){
5 | var parameters = getPostsParameters(terms),
6 | posts = Posts.find(parameters.find, parameters.options);
7 |
8 | return posts;
9 | }
10 | return [];
11 | });
12 |
13 | // Publish all the users that have posted the currently displayed list of posts
14 | // plus the commenters for each post
15 |
16 | Meteor.publish('postsListUsers', function(terms) {
17 | if(can.viewById(this.userId)){
18 | var parameters = getPostsParameters(terms),
19 | posts = Posts.find(parameters.find, parameters.options),
20 | postsIds = _.pluck(posts.fetch(), '_id'),
21 | userIds = _.pluck(posts.fetch(), 'userId');
22 |
23 | // for each post, add first four commenter's userIds to userIds array
24 | posts.forEach(function (post) {
25 | userIds = userIds.concat(_.first(post.commenters,4));
26 | });
27 |
28 | userIds = _.unique(userIds);
29 |
30 | return Meteor.users.find({_id: {$in: userIds}}, {fields: avatarOptions, multi: true});
31 | }
32 | return [];
33 | });
34 |
--------------------------------------------------------------------------------
/server/publications/settings.js:
--------------------------------------------------------------------------------
1 | Meteor.publish('settings', function() {
2 | var options = {};
3 | var privateFields = {};
4 |
5 | // look at SettingsSchema to see which fields should be kept private
6 | _.each(SettingsSchema._schema, function( val, key ) {
7 | if (val.autoform && !!val.autoform.private)
8 | privateFields[key] = false;
9 | });
10 |
11 | if(!isAdminById(this.userId)){
12 | options = _.extend(options, {
13 | fields: privateFields
14 | });
15 | }
16 | return Settings.find({}, options);
17 | });
--------------------------------------------------------------------------------
/server/publications/single_post.js:
--------------------------------------------------------------------------------
1 | // Publish a single post
2 |
3 | Meteor.publish('singlePost', function(id) {
4 | if (can.viewById(this.userId)){
5 | return Posts.find(id);
6 | }
7 | return [];
8 | });
9 |
10 | // Publish authors of the current post and its comments
11 |
12 | Meteor.publish('postUsers', function(postId) {
13 | if (can.viewById(this.userId)){
14 | // publish post author and post commenters
15 | var post = Posts.findOne(postId),
16 | users = [];
17 |
18 | if (post) {
19 | var comments = Comments.find({postId: post._id}).fetch();
20 | // get IDs from all commenters on the post, plus post author's ID
21 | users = _.pluck(comments, "userId");
22 | users.push(post.userId);
23 | users = _.unique(users);
24 | }
25 |
26 | return Meteor.users.find({_id: {$in: users}}, {fields: privacyOptions});
27 | }
28 | return [];
29 | });
30 |
31 | // Publish comments for a specific post
32 |
33 | Meteor.publish('postComments', function(postId) {
34 | if (can.viewById(this.userId)){
35 | return Comments.find({postId: postId});
36 | }
37 | return [];
38 | });
--------------------------------------------------------------------------------
/server/publications/users.js:
--------------------------------------------------------------------------------
1 | // Publish the current user
2 |
3 | Meteor.publish('currentUser', function() {
4 | var user = Meteor.users.find({_id: this.userId});
5 | return user;
6 | });
7 |
8 | // publish all users for admins to make autocomplete work
9 | // TODO: find a better way
10 |
11 | Meteor.publish('allUsersAdmin', function() {
12 | var selector = getSetting('requirePostInvite') ? {isInvited: true} : {}; // only users that can post
13 | if (isAdminById(this.userId)) {
14 | return Meteor.users.find(selector, {fields: {
15 | _id: true,
16 | profile: true,
17 | slug: true
18 | }});
19 | }
20 | return [];
21 | });
22 |
--------------------------------------------------------------------------------
/server/publications/users_dashboard.js:
--------------------------------------------------------------------------------
1 | // Publish all users
2 |
3 | Meteor.publish('allUsers', function(filterBy, sortBy, limit) {
4 | if(isAdminById(this.userId)){
5 | var parameters = getUsersParameters(filterBy, sortBy, limit);
6 | return Meteor.users.find(parameters.find, parameters.options);
7 | }
8 | return [];
9 | });
10 |
--------------------------------------------------------------------------------
/server/start.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function () {
2 | logEvent({
3 | name: "firstRun",
4 | unique: true, // will only get logged a single time
5 | important: true
6 | })
7 | });
8 |
9 | if (getSetting('mailUrl'))
10 | process.env.MAIL_URL = getSetting('mailUrl');
11 |
--------------------------------------------------------------------------------
/server/start_cron.js:
--------------------------------------------------------------------------------
1 | Meteor.startup(function() {
2 | SyncedCron.start();
3 | });
4 |
--------------------------------------------------------------------------------
/server/testing.js:
--------------------------------------------------------------------------------
1 | var isTesting = Meteor.settings && Meteor.settings.isTesting;
2 |
3 | if (isTesting) {
4 | console.log('Adding login functions');
5 | Meteor.methods({
6 | // login from client with Meteor.call('loginTest', function(err, res) { Meteor.loginWithToken(res, function() {}); })
7 | loginTest: function() {
8 | var login, token;
9 | Meteor.users.remove({});
10 | login = Accounts.updateOrCreateUserFromExternalService("sandstorm", {
11 | id: 0,
12 | permissions: ['admin']
13 | }, {
14 | profile: {
15 | name: 'Test Admin'
16 | }
17 | });
18 | console.log(login);
19 | token = Accounts._generateStampedLoginToken();
20 | Accounts._insertLoginToken(login.userId, token);
21 | return token.token;
22 | }
23 | });
24 | }
25 |
--------------------------------------------------------------------------------
/testing.settings.json:
--------------------------------------------------------------------------------
1 | {"isTesting" : true}
2 |
--------------------------------------------------------------------------------